package com.dhcc.sds.busi.service.impl;

import cn.hutool.json.JSONUtil;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.mapper.EntityWrapper;
import com.baomidou.mybatisplus.mapper.Wrapper;
import com.dhcc.cdc.busi.dao.*;
import com.dhcc.cdc.busi.entity.*;
import com.dhcc.cdc.busi.service.ICdcDictionaryService;
import com.dhcc.cdc.sys.cache.config.CdcConfigCache;
import com.dhcc.cdc.sys.dao.DictionaryMapper;
import com.dhcc.cdc.sys.entity.DictionaryEntity;
import com.dhcc.cdc.sys.service.IConfigurationService;
import com.dhcc.core.framework.util.CommonUtil;
import com.dhcc.core.framework.util.SpringContextHolder;
import com.dhcc.sdc.api.dao.SdsToolSdkMapper;
import com.dhcc.sdc.base.dao.SdcBaseAssessmenentryMapper;
import com.dhcc.sdc.base.entity.SdcBaseAssessmenentryEntity;
import com.dhcc.sdc.busi.dao.SdcBusiEvaluationHisMapper;
import com.dhcc.sdc.busi.dao.SdcBusiEvaluationItemMapper;
import com.dhcc.sdc.busi.dao.SdcBusiEvaluationMapper;
import com.dhcc.sdc.busi.entity.SdcBusiEvaluationEntity;
import com.dhcc.sdc.busi.entity.SdcBusiEvaluationHisEntity;
import com.dhcc.sdc.busi.entity.SdcBusiEvaluationItemEntity;
import com.dhcc.sds.base.cache.formitem.FormItemCache;
import com.dhcc.sds.base.cache.formitemdic.FormItemDicCache;
import com.dhcc.sds.base.cache.formitemdic.IFormItemDicCache;
import com.dhcc.sds.base.cache.formitemmatchrule.FormItemMatchRuleCache;
import com.dhcc.sds.base.cache.qcentity.QcEntityCache;
import com.dhcc.sds.base.dao.*;
import com.dhcc.sds.base.entity.*;
import com.dhcc.sds.base.function.GetEntrySrv;
import com.dhcc.sds.busi.dao.SdsQcFormShowMapper;
import com.dhcc.sds.busi.dao.SdsQcfitemExecresultMapper;
import com.dhcc.sds.busi.dao.SdsQcincaseMapper;
import com.dhcc.sds.busi.dao.SdsQcincaseOperlogMapper;
import com.dhcc.sds.busi.dto.SdsQcFormItemDto;
import com.dhcc.sds.busi.entity.SdsQcfitemExecresultEntity;
import com.dhcc.sds.busi.entity.SdsQcincaseEntity;
import com.dhcc.sds.busi.entity.SdsQcincaseOperlogEntity;
import com.dhcc.sds.busi.service.ISdsQcFormShowService;
import com.dhcc.sds.busi.service.ISdsQcfitemExecresultService;
import com.dhcc.sds.busi.service.ISdsQcincaseDataService;
import com.dhcc.sds.standard.dao.SdsStandDicMatchMapper;
import com.dhcc.sds.standard.dao.SdsStandDicMatchParamMapper;
import com.dhcc.sds.standard.dao.SdsStandSourceMapper;
import com.dhcc.sds.standard.dto.CdcExaminateDto;
import com.dhcc.sds.standard.dto.CdcLisReportDto;
import com.dhcc.sds.standard.dto.CdcNurDto;
import com.dhcc.sds.standard.dto.CdcOrdmastDto;
import com.dhcc.sds.standard.entity.SdsStandDicMatchEntity;
import com.dhcc.sds.standard.entity.SdsStandDicMatchParamEntity;
import com.dhcc.sds.standard.entity.SdsStandRuleBaseEntity;
import com.dhcc.sds.standard.entity.SdsStandSourceEntity;
import com.dhcc.sds.standard.service.ISdsStandDicService;
import com.dhcc.sds.standard.service.ISdsStandRuleBaseService;
import com.dhcc.sds.standard.service.IsdsStandRuleCalService;
import com.dhcc.sds.util.DateUtil;
import com.dhcc.sds.util.IdentityCodeUtil;
import com.dhcc.sds.ws.dhcmessage.DHCMessageServiceLocator;
import com.dhcc.sds.ws.dhcmessage.DHCMessageServiceSoap;
import com.googlecode.aviator.AviatorEvaluator;
import io.swagger.models.auth.In;
import org.apache.commons.jexl2.Expression;
import org.apache.commons.jexl2.JexlContext;
import org.apache.commons.jexl2.JexlEngine;
import org.apache.commons.jexl2.MapContext;
import org.apache.commons.lang.StringEscapeUtils;
import org.apache.commons.lang.text.StrSubstitutor;
import org.apache.cxf.endpoint.Client;
import org.apache.cxf.jaxws.endpoint.dynamic.JaxWsDynamicClientFactory;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.util.EntityUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.transaction.PlatformTransactionManager;
import org.springframework.transaction.TransactionDefinition;
import org.springframework.transaction.TransactionStatus;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.transaction.support.DefaultTransactionDefinition;
import org.springframework.util.CollectionUtils;
import org.springframework.util.StringUtils;

import javax.annotation.Resource;
import javax.script.ScriptEngine;
import javax.script.ScriptEngineManager;
import javax.script.ScriptException;
import javax.xml.rpc.ServiceException;
import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.lang.reflect.Method;
import java.math.BigDecimal;
import java.rmi.RemoteException;
import java.text.DecimalFormat;
import java.util.*;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.stream.Collectors;

/**
 * @version 1.0 DHCC
 * @Description: 描述
 * @Project Name:
 * @Package Name:
 * @File Name:
 * @author:sunyingjie
 * @date:
 * @Copyright: (c) DHCC All rights reserved.
 */
@Service("sdsQcFormShowService")
public class SdsQcFormShowServiceImpl implements ISdsQcFormShowService {
    @Autowired
    private SdsQcfitemMatchRuleMapper sdsQcfitemMatchRuleMapper;
    @Autowired
    private SdsQcformItemMapper sdsQcformItemMapper;
    @Autowired
    private SdsQcfitemDicMapper sdsQcfitemDicMapper;
    @Autowired
    private SdsQcincaseMapper sdsQcincaseMapper;
    @Autowired
    private SdsQcfitemExecresultMapper sdsQcfitemExecresultMapper;
    @Autowired
    private IConfigurationService configurationService;
    @Autowired
    private SdsQcentityMapper sdsQcentityMapper;
    @Autowired
    private SdcBusiEvaluationItemMapper sdcBusiEvaluationItemMapper;
    @Autowired
    private SdsQcFormShowMapper sdsQcFormShowMapper;
    @Autowired
    private SdsDataConfigMapper sdsDataConfigMapper;
    @Autowired
    private DictionaryMapper dictionaryMapper;
    @Autowired
    private CdcEpisodeMapper cdcEpisodeMapper;
    @Autowired
    private CdcOrdexecMapper cdcOrdexecMapper;
    @Autowired
    private CdcOrdmastMapper cdcOrdmastMapper;
    @Autowired
    private CdcDiagnosisMapper cdcDiagnosisMapper;
    @Autowired
    private CdcEmrMapper cdcEmrMapper;
    @Autowired
    private CdcSurgeryMapper cdcSurgeryMapper;
    @Autowired
    private CdcEprMapper cdcEprMapper;
    @Autowired
    private CdcExaminateMapper cdcExaminateMapper;
    @Autowired
    private CdcBsExamStructMapper cdcBsExamStructMapper;
    @Autowired
    private CdcLabVisitMapper cdcLabVisitMapper;
    @Autowired
    private CdcLabReportMapper cdcLabReportMapper;
    @Autowired
    private CdcLabResultMapper cdcLabResultMapper;
    @Autowired
    private CdcLabItemMapper cdcLabItemMapper;
    @Autowired
    private CdcLabSetMapper cdcLabSetMapper;
    @Autowired
    private CdcLabOrderMapper cdcLabOrderMapper;
    @Autowired
    private CdcSignMapper cdcSignMapper;
    @Autowired
    private CdcNurMapper cdcNurMapper;
    @Autowired
    private CdcDictionaryMapper cdcDictionaryMapper;
    @Autowired
    private ICdcDictionaryService cdcDictionaryService;
    @Resource
    private SdsStandDicMatchMapper sdsStandDicMatchMapper;
    @Autowired
    private SdsFunctionMapper sdsFunctionMapper;
    @Autowired
    private ISdsQcfitemExecresultService sdsQcfitemExecresultService;
    @Autowired
    private ISdsStandDicService sdsStandDicService;
    @Autowired
    private SdsStandSourceMapper sdsStandSourceMapper;
    @Autowired
    private SdsStandDicMatchParamMapper sdsStandDicMatchParamMapper;
    @Autowired
    private SdcBusiEvaluationMapper sdcBusiEvaluationMapper;
    @Autowired
    private SdsToolSdkMapper sdsToolSdkMapper;
    @Autowired
    private IsdsStandRuleCalService isdsStandRuleCalService;
    @Autowired
    private ISdsStandRuleBaseService iSdsStandRuleBaseService;
    @Resource
    private SdcBusiEvaluationHisMapper sdcBusiEvaluationHisMapper;
    @Autowired
    private SdcBaseAssessmenentryMapper sdcBaseAssessmenentryMapper;
    @Autowired
    private CdcTransferMapper cdcTransferMapper;
    @Autowired
    private CdcLocationMapper cdcLocationMapper;
    @Autowired
    private SdsQcentityRuleMapper sdsQcentityRuleMapper;
    @Autowired
    private SdsExpressMapper sdsExpressMapper;
    @Autowired
    private PlatformTransactionManager platformTransactionManager;
    @Autowired
    private SdsQcincaseOperlogMapper sdsQcincaseOperlogMapper;
    @Autowired
    private ISdsQcincaseDataService sdsQcincaseDataService;
    @Autowired
    private GetEntrySrv getEntrySrv;
    //获取his发布的接口地址
    @Value("${sys.dhcHisCacheIp}")
    private String dhcHisCacheIp;

    @Value("${sys.dhcHisCachePath}")
    private String dhcHisCachePath;

    //东华HIS对外接口是否有head验证 true 有 false无
    @Value("${sys.dhcHisInterfaceHead}")
    private boolean dhcHisInterfaceHead;

    /**
     * 小括号及其里面内容
     */
    private static String p1 = "\\(.*?\\)";
    /**
     * 中括号及其里面内容
     */
    private static String p2 = "\\[.*?\\]";
    /**
     * 大括号及其里面内容
     */
    private static String p3 = "\\{.*?\\}";

    private Logger logger = LoggerFactory.getLogger(this.getClass());

    @Override
    public JSONArray getRuleLinkItem(Map<String, Object> params) {
        Long entityId = Long.valueOf(params.get("entityId").toString());
        Long formItemId = Long.valueOf(params.get("formItemId").toString());
        JSONArray array = new JSONArray();
        // 查询项目校验规则
//        Wrapper<SdsQcfitemMatchRuleEntity> wrapper = new EntityWrapper<>();
//        wrapper.eq("form_item_id", formItemId);
//        List<SdsQcfitemMatchRuleEntity> ruleList = sdsQcfitemMatchRuleMapper.selectList(wrapper);
        List<SdsQcfitemMatchRuleEntity> ruleList = FormItemMatchRuleCache.me().getFormItemMatchRuleList(formItemId);
        // 查找规则公式中括号以内的字符
        Pattern p = Pattern.compile(p1);
        for (SdsQcfitemMatchRuleEntity rule : ruleList) {
            String ruleExp = rule.getControlExp();
            if (CommonUtil.isEmpty(ruleExp)) {
                continue;
            }
            Matcher m = p.matcher(ruleExp);
            // 遍历找到的所有括号
            while (m.find()) {
                if (m.group().contains("\"")) {
                    // 括号内是常量，跳到下一循环
                    continue;
                }
                String itemCode = m.group().substring(1, m.group().length() - 1);
//                SdsQcformItemEntity formItem = new SdsQcformItemEntity();
//                formItem.setEntityId(entityId);
//                formItem.setBtCode(itemCode);
//                formItem = sdsQcformItemMapper.selectOne(formItem);
                SdsQcformItemEntity formItem = FormItemCache.me().getFormItemByCode(entityId, itemCode);
                JSONObject obj = new JSONObject();
                obj.put("itemId", formItem.getId());
                obj.put("itemCode", itemCode);
                array.add(obj);
            }
        }

        return array;
    }

    @Override
    public JSONArray getValidMsg(Map<String, Object> params) throws ScriptException {
        JSONArray validMsg = new JSONArray();
        // 当前项目Code
        String formItemCode = params.get("formItemCode").toString();
        // 关联项目code和值
        JSONArray formItemLinkArr = JSONArray.parseArray((String) params.get("formItemLink"));
        // 当前项目类型
        String itemType = params.get("formItemType").toString();
        // 当前项目值
        String itemValue = params.get("formItemValue").toString();
        // 当前日期
        Long now = System.currentTimeMillis() / 1000; // 因为M那边配的表达式精度为秒，所以除1000
        //1、ScriptEngineManager是JDK6提出的相关方法，这方式的主要目的就是用来对脚本语言的处理。
        //2、ScriptEngineManager是在java的javax.script的包下，是Java原生提供的脚本语言处理方法。
        ScriptEngineManager manager = new ScriptEngineManager();
        ScriptEngine engine = manager.getEngineByName("JavaScript");
        // 查找规则公式中括号以内的字符
        Pattern p = Pattern.compile(p1);// 查找规则公式中括号以内的字符

        Map tmpItemMap = new HashMap();
        for (int i = formItemLinkArr.size() - 1; i >= 0; i--) {
            JSONObject obj = formItemLinkArr.getJSONObject(i);
            tmpItemMap.put(obj.get("itemCode"), obj.get("itemVal"));
        }

        // 查询项目校验规则
//        List<SdsQcfitemMatchRuleEntity> ruleList = sdsQcfitemMatchRuleMapper.list(params);
        List<SdsQcfitemMatchRuleEntity> ruleList = FormItemMatchRuleCache.me().getFormItemMatchRuleList(Long.valueOf(params.get("formItemId").toString()));
        rLoop:
        for (SdsQcfitemMatchRuleEntity rule : ruleList) {
            JSONObject msgObj = new JSONObject();
            String levelType = rule.getLevelDict().getCode(); // 规则类型：Info、Warning、Error、Stop
            String ruleFunction = rule.getExpDict().getExpCode(); // 函数类型
            if (CommonUtil.isEmpty(ruleFunction)) {
                continue;
            } // 函数类型为空，跳到下一条
            String ruleTips = rule.getTipText(); // 规则提示信息
            String ruleExpress = rule.getControlExp(); //规则表达式
            boolean valiResult = false;//当前规则结果
            switch (ruleFunction) {
                case "DATEFORMAT": // 日期格式
                    if ("Date".equals(itemType)) {
                        if (!DateUtil.isValidDate(itemValue)) {
                            ruleTips += "yyyy-MM-dd";
                            msgObj.put("msgContent", ruleTips);
                            msgObj.put("msgType", levelType);
                            validMsg.add(msgObj);
                            valiResult = true;
                        }
                    } else if ("DateT".equals(itemType)) {
                        if (!DateUtil.isValidDateTime(itemValue)) {
                            ruleTips += "yyyy-MM-dd HH:mm:ss";
                            msgObj.put("msgContent", ruleTips);
                            msgObj.put("msgType", levelType);
                            validMsg.add(msgObj);
                            valiResult = true;
                        }
                    }
                    break;
                case "ITEMLEN":  // 长度限制
                    if ("Text".equals(itemType)) {
                        int strLen = itemValue.length();
                        ruleExpress = ruleExpress.replace("this", String.valueOf(strLen));
                    } else {
                        int strLen = itemValue.split(",").length;
                        ruleExpress = ruleExpress.replace("this", String.valueOf(strLen));
                    }
                    if (!(boolean) engine.eval(ruleExpress)) {
                        msgObj.put("msgContent", ruleTips);
                        msgObj.put("msgType", levelType);
                        validMsg.add(msgObj);
                        valiResult = true;
                    }
                    break;
                case "CMPVAL": // 值结果比较
                    if (itemType.contains("Date")) {
                        long thisValue = DateUtil.getTime(itemValue) / 1000; // 因为M那边配的表达式精度为秒，所以除1000
                        ruleExpress = ruleExpress.replace("this", String.valueOf(thisValue));
                        // 替换关联项目的值
                        Matcher m = p.matcher(ruleExpress);
                        while (m.find()) {// 遍历找到的所有小括号
                            // 取得关联项目代码
                            String itemCode = m.group().substring(1, m.group().length() - 1);
                            if (CommonUtil.isEmpty(tmpItemMap.get(itemCode))) {
                                continue rLoop;
                            }
                            // 从临时集合取得关联项目的值
                            long xitemVal = DateUtil.getTime(tmpItemMap.get(itemCode).toString()) / 1000;
                            ruleExpress = ruleExpress.replace(itemCode, String.valueOf(xitemVal));
                        }
                    } else {
                        if ("CM-6-1".equals(formItemCode)) {
                            // 替换关联项目的值
                            Matcher m = p.matcher(ruleExpress);
                            boolean flg = false;
                            while (m.find()) {// 遍历找到的所有括号
                                flg = true;
                                // 取得关联项目代码
                                String itemCode = m.group().substring(1, m.group().length() - 1);
                                if (CommonUtil.isEmpty(tmpItemMap.get(itemCode))) {
                                    continue rLoop;
                                }
                                // 从临时集合取得关联项目的值
                                String xitemVal = tmpItemMap.get(itemCode).toString();
                                ruleExpress = ruleExpress.replace("(" + itemCode + ")", String.valueOf(new BigDecimal(xitemVal).multiply(BigDecimal.valueOf(100)).longValue()));
                            }
                            if (flg) { // 如果没有括号，说明只是简单的比较值，只替换当前总费用值，等号右边是常量
                                ruleExpress = ruleExpress.replace("this", String.valueOf(new BigDecimal(itemValue).multiply(BigDecimal.valueOf(100)).longValue()));
                            } else {
                                ruleExpress = ruleExpress.replace("this", itemValue);
                            }
                        } else {
                            // 如果表达式有引号，那么是字符串比较，给项目值加上双引号
                            if (ruleExpress.contains("\"")) {
                                itemValue = "\"" + itemValue + "\"";
                            }
                            ruleExpress = ruleExpress.replace("this", itemValue);
                            // 替换关联项目的值
                            Matcher m = p.matcher(ruleExpress);
                            while (m.find()) {// 遍历找到的所有括号
                                if (m.group().contains("\"")) {
                                    continue; // 常量，跳到下一个
                                }

                                // 取得关联项目代码
                                String itemCode = m.group().substring(1, m.group().length() - 1);
                                if (CommonUtil.isEmpty(tmpItemMap.get(itemCode))) {
                                    continue rLoop;
                                }
                                // 从临时集合取得关联项目的值
                                String xitemVal = tmpItemMap.get(itemCode).toString();
                                ruleExpress = ruleExpress.replace("(" + itemCode + ")", xitemVal);
                            }
                        }
                    }
                    ruleExpress = ruleExpress.replace("Now", String.valueOf(now));
                    // 将表达式中的大括号中括号替换为小括号，以及其他其他字符替换为可执行字符
                    ruleExpress = ruleExpress.replace("{", "(").replace("}", ")");
                    ruleExpress = ruleExpress.replace("[", "(").replace("]", ")");

                    if (!(boolean) engine.eval(ruleExpress)) {
                        msgObj.put("msgContent", ruleTips);
                        msgObj.put("msgType", levelType);
                        validMsg.add(msgObj);
                        valiResult = true;
                    }
                    break;
                case "IDFORMAT": // 身份证号格式
                    if (CommonUtil.isNotEmpty(itemValue) && CommonUtil.notEquals(itemValue, "/") && !IdentityCodeUtil.isIDCardNo(itemValue)) {
                        msgObj.put("msgContent", ruleTips);
                        msgObj.put("msgType", levelType);
                        validMsg.add(msgObj);
                        valiResult = true;
                    }
                    break;
                default:
                    break;
            }
            // 如果没有规则触发，继续下一条规则
            if (!valiResult) {
                continue rLoop;
            }
            //如果有错误 或者 终止上报的错误，则不再校验后面的规则
            if ("Error".equals(levelType) || "Stop".equals(levelType)) {
                break rLoop;
            }
        }

        return validMsg;
    }

    /**
     * 计算本项目的显隐属性
     *
     * @param mrListId
     * @param formItem
     * @return
     * @throws ScriptException
     */
    @Override
    public Integer calcTriggerExp(Long mrListId, SdsQcformItemEntity formItem, Map<String, Object> editMap) {
        // 项目全部默认显示
        Integer editPower = 1;
        //1、ScriptEngineManager是JDK6提出的相关方法，这方式的主要目的就是用来对脚本语言的处理。
        //2、ScriptEngineManager是在java的javax.script的包下，是Java原生提供的脚本语言处理方法。
        ScriptEngineManager manager = new ScriptEngineManager();
        ScriptEngine engine = manager.getEngineByName("JavaScript");
        if (CommonUtil.isEmpty(formItem.getTriggerExp())) {
            return editPower;
        } else {
            // 带表达式的项目默认不显示，只有表达式条件成立之后才显示
            editPower = 0;
            String triggerExp = formItem.getTriggerExp();
            Long entityId = formItem.getEntityId();
            // 查找规则公式中括号以内的字符
            Pattern p = Pattern.compile(p1);// 查找规则公式中括号以内的字符
            // 替换关联项目的值
            Matcher m = p.matcher(triggerExp);
            while (m.find()) {// 遍历找到的所有括号
                if (m.group().contains("\"")) { // 如果里面是常量，则继续下一个
                    continue;
                }
                // 取得关联项目代码
                String itemCode = m.group().substring(1, m.group().length() - 1);
                // 通过项目代码查询项目id并取值
//                SdsQcformItemEntity linkItem = new SdsQcformItemEntity();
//                linkItem.setEntityId(entityId);
//                linkItem.setBtCode(itemCode);
//                linkItem = sdsQcformItemMapper.selectOne(linkItem);
                String linkVal = "";
                if (editMap.get(itemCode) != null && (Integer) editMap.get(itemCode) == 0) {
                    linkVal = "";
                } else {
                    SdsQcformItemEntity linkItem = FormItemCache.me().getFormItemByCode(entityId, itemCode);

                    SdsQcfitemExecresultEntity linkItemExec = new SdsQcfitemExecresultEntity();
                    linkItemExec.setformItemId(linkItem.getId());
                    linkItemExec.setInCaseId(mrListId);
                    linkItemExec = sdsQcfitemExecresultMapper.selectOne(linkItemExec);
                    // 如果有项目值为空，则默认不符合
                    if (!CommonUtil.isEmpty(linkItemExec)) {
                        linkVal = linkItemExec.getItemResult();
                    }
                }
                // 如果表达式有引号，那么是字符串比较，给项目值加上双引号
//                if (triggerExp.contains("\"")) {
                linkVal = "(\"" + linkVal + "\")";
//                }
                // 将值替换表达式中项目代码
                triggerExp = triggerExp.replace(m.group(), linkVal);
            }
            if (!triggerExp.matches(p3)) {
                String[] expArr = triggerExp.split(":", 2);
                String subExpType_l = expArr[0];
                String subExp_l = expArr[1];

                long divisor = 1;
                if (subExpType_l.contains("CALC")) {
                    switch (subExpType_l) {
                        case "CALC-h":
                            // 1小时毫秒数
                            divisor = 60 * 60 * 1000;
                            break;
                        case "CALC-m":
                            // 一分钟毫秒数
                            divisor = 60 * 1000;
                            break;
                        case "CALC-day":
                            // 一天毫秒数
                            divisor = 24 * 60 * 60 * 1000;
                            break;
                        case "CALC-month":
                            // 一个月毫秒数
                            divisor = 30l * 24l * 60l * 60l * 1000l;
                            break;
                        case "CALC-year":
                            // 一年毫秒数
                            divisor = 12l * 30l * 24l * 60l * 60l * 1000l;
                            break;
                        default:
                            break;
                    }
                    // 查找规则公式中小括号以内的值
                    // 替换关联项目的值
                    m = p.matcher(subExp_l);
                    String execExp = subExp_l;
                    while (m.find()) {
                        if ("()".equals(m.group()) || "(\"\")".equals(m.group())) {
                            execExp = execExp.replace(m.group(), "0");
                            continue;
                        }
                        String val = m.group().substring(1, m.group().length() - 1).replace("\"", "");
                        Long times = DateUtil.getTime(val);
                        int minutes = Math.toIntExact(times / divisor);
                        execExp = execExp.replace(val, String.valueOf(minutes));
                    }
                    triggerExp = triggerExp.replace(subExp_l, execExp);
                }
                triggerExp = triggerExp.replace(subExpType_l, "");
            } else {
                // 查找规则公式中大括号以内的字符
                Pattern pat3 = Pattern.compile(p3);
                // 替换关联项目的值
                Matcher m3 = pat3.matcher(triggerExp);
                while (m3.find()) {
                    // 大括号中间的表达式
                    String subExpStr_l = m3.group().substring(1, m3.group().length() - 1);
                    String[] expArr = subExpStr_l.split(":", 2);
                    String subExpType_l = expArr[0];
                    String subExp_l = expArr[1];

                    long divisor = 1;
                    if (subExpType_l.contains("CALC")) {
                        switch (subExpType_l) {
                            case "CALC-h":
                                // 1小时毫秒数
                                divisor = 60 * 60 * 1000;
                                break;
                            case "CALC-m":
                                // 一分钟毫秒数
                                divisor = 60 * 1000;
                                break;
                            case "CALC-day":
                                // 一天毫秒数
                                divisor = 24 * 60 * 60 * 1000;
                                break;
                            case "CALC-month":
                                // 一个月毫秒数
                                divisor = 30l * 24l * 60l * 60l * 1000l;
                                break;
                            case "CALC-year":
                                // 一年毫秒数
                                divisor = 12l * 30l * 24l * 60l * 60l * 1000l;
                                break;
                            default:
                                break;
                        }
                        // 查找规则公式中小括号以内的值
                        // 替换关联项目的值
                        m = p.matcher(subExp_l);
                        String execExp = subExp_l;
                        while (m.find()) {
                            if ("()".equals(m.group()) || "(\"\")".equals(m.group())) {
                                execExp = execExp.replace(m.group(), "0");
                                continue;
                            }
                            String val = m.group().substring(1, m.group().length() - 1).replace("\"", "");
                            Long times = DateUtil.getTime(val);
                            int minutes = Math.toIntExact(times / divisor);
                            execExp = execExp.replace(val, String.valueOf(minutes));
                        }
                        triggerExp = triggerExp.replace(subExp_l, execExp);
                    }
                    triggerExp = triggerExp.replace(subExpStr_l, subExp_l);
                    triggerExp = triggerExp.replace(subExpType_l, "");
                }
            }
            triggerExp = triggerExp.replace(":", "");
            if (triggerExp.contains("contains")) {
                triggerExp = modifyExpression(triggerExp);
            }
            // 将表达式中的大括号中括号替换为小括号，以及其他其他字符替换为可执行字符
            triggerExp = triggerExp.replace("{", "(").replace("}", ")");
            triggerExp = triggerExp.replace("[", "(").replace("]", ")");
            triggerExp = triggerExp.replace("contains(\"\")", "contains(\",,\")");
            triggerExp = triggerExp.replace("oth", "OTH").replace("def", "DEF");

            // 运算前置条件表达式
            try {
                if ((boolean) engine.eval(triggerExp)) {
                    editPower = 1;
                }
            } catch (ScriptException e) {
                // 表达式解析失败，默认返回1
                return 1;
            }
        }
        return editPower;
    }

    @Override
    public JSONArray getTriggerLinkItem(Map<String, Object> params) {
        Long entityId = Long.valueOf(params.get("entityId").toString());
        Long formItemId = Long.valueOf(params.get("formItemId").toString());
        String formItemCode = "(" + params.get("formItemCode").toString() + ")";
        JSONArray array = new JSONArray();
        // 查询关联此项目的项目
        List<SdsQcformItemEntity> linkItemList = FormItemCache.me().getFormItemByExp(entityId, formItemCode);
        for (int i = linkItemList.size() - 1; i >= 0; i--) {
            JSONObject obj = new JSONObject();
            SdsQcformItemEntity item = linkItemList.get(i);
            // 替换关联项目的值
            // 查找规则公式中括号以内的字符
            Pattern p = Pattern.compile(p1);// 查找规则公式中括号以内的字符
            Matcher m = p.matcher(item.getTriggerExp());
            JSONArray linkArr = new JSONArray();
            while (m.find()) {// 遍历找到的所有括号
                if (m.group().contains("\"")) { // 如果里面是常量，则继续下一个
                    continue;
                }
                JSONObject linkObj = new JSONObject();
                // 取得关联项目代码
                String itemCode = m.group().substring(1, m.group().length() - 1);
                SdsQcformItemEntity formItem = FormItemCache.me().getFormItemByCode(entityId, itemCode);

                linkObj.put("itemId", formItem.getId());
                linkObj.put("itemCode", itemCode);
                linkArr.add(linkObj);
            }
            obj.put("itemId", item.getId());
            obj.put("itemCode", item.getBtCode());
            obj.put("triExp", item.getTriggerExp());
            obj.put("itemIndNo", item.getBtIndNo());
            obj.put("linkItem", linkArr);
            array.add(obj);
        }

        return array;
    }

    @Override
    public JSONArray getLinkItemMsg(Map<String, Object> params) throws ScriptException, UnsupportedEncodingException {
        JSONArray arr = new JSONArray();
        Long curFormItemId = Long.valueOf(params.get("formItemId").toString());
        Long entityId = Long.valueOf(params.get("entityId").toString());
        // 关联项目信息及它的关联项目
        JSONArray itemArr = JSONArray.parseArray(java.net.URLDecoder.decode(params.get("formItemLink").toString(), "UTF-8"));

        Map<String, Object> editPowerMap = new HashMap<>();
        Map<String, Object> showItemMap = new HashMap<>();
        for (int i = itemArr.size() - 1; i >= 0; i--) {
            JSONObject obj = itemArr.getJSONObject(i);
            if (showItemMap.get(obj.getString("itemCode")) != null) {
                continue;
            }
            // 计算显隐性
            Map resMap = this.calcExpReslut(obj, editPowerMap);
            arr.add(resMap);
            editPowerMap.put(obj.getString("itemCode"), resMap.get("showFlg"));
            // 如果项目为显示状态，则不再处理关联它的项目，反之继续查找关联它的项目并隐藏
            if ("1".equals(resMap.get("showFlg").toString())) {
                showItemMap.put(obj.getString("itemCode"), 1);
                continue;
            } else {
                // 查询关联此项目的项目
                Set<SdsQcformItemEntity> linkItemList = new HashSet<>();
                linkItemList = findSubItems(entityId, obj.getString("itemCode"), linkItemList);
                // 将孙项目设置为隐藏
                for (SdsQcformItemEntity item : linkItemList) {
                    Map subMap = new HashMap();
                    if (item.getId().equals(curFormItemId) || editPowerMap.get(item.getBtCode()) != null || showItemMap.get(item.getBtCode()) != null) {
                        continue;
                    }
                    subMap.put("itemId", item.getId());
                    subMap.put("itemCode", item.getBtCode());
                    subMap.put("showFlg", "0");
                    arr.add(subMap);
                }
            }
        }
        return arr;
    }

    @Override
    public JSONArray getLogicLinkItem(Map<String, Object> params) {
        JSONArray array = new JSONArray();
        Long entityId = Long.valueOf(params.get("entityId").toString());
        Long formItemId = Long.valueOf(params.get("formItemId").toString());
        String formItemCode = params.get("formItemCode").toString();
        // 查找数据源配置中逻辑表达式含有当前项目code的项目
        List<SdsDataConfigEntity> logicItemConfig = sdsDataConfigMapper.selectList(new EntityWrapper<SdsDataConfigEntity>().like("calc_exp", "(" + formItemCode + ")").isNotNull("fitem_dic_id"));
        for (SdsDataConfigEntity dataConfig : logicItemConfig) {
            JSONObject obj = new JSONObject();
            // 获取当前配置的项目信息，如果当前项目不是当前病种的，则跳过
            SdsQcformItemEntity linkItem = FormItemCache.me().getFormItemById(dataConfig.getFitemId());
            if (CommonUtil.notEquals(linkItem.getEntityId(), entityId)) {
                continue;
            }
            String linkCalcExp = dataConfig.getCalcExp();
            // 查找规则公式中括号以内的字符
            Pattern p = Pattern.compile(p1);// 查找规则公式中括号以内的字符
            Matcher m = p.matcher(linkCalcExp);
            JSONArray linkArr = new JSONArray();
            while (m.find()) {// 遍历找到的所有括号
                if (m.group().contains("\"")) { // 如果里面是常量，则继续下一个
                    continue;
                }
                JSONObject linkObj = new JSONObject();
                // 取得关联项目代码
                String itemCode = m.group().substring(1, m.group().length() - 1);
                SdsQcformItemEntity formItem = FormItemCache.me().getFormItemByCode(entityId, itemCode);

                linkObj.put("itemId", formItem.getId());
                linkObj.put("itemCode", itemCode);
                linkArr.add(linkObj);
            }
            // 获取当前值域选项
            SdsQcfitemDicEntity itemDic = sdsQcfitemDicMapper.selectById(dataConfig.getFitemDicId());
            obj.put("itemId", linkItem.getId());
            obj.put("itemDicId", dataConfig.getFitemDicId());
            obj.put("itemDicCode", itemDic.getCode());
            obj.put("calcExp", dataConfig.getCalcExp());
            obj.put("expItems", linkArr);
            array.add(obj);
        }
        return array;
    }

    @Override
    public JSONObject getLinkItemDefaultVal(Map<String, Object> params) {
        JSONObject objRsult = new JSONObject();
        // 关联项目信息及它的关联项目
        JSONArray itemArr = null;
        try {
            itemArr = JSONArray.parseArray(java.net.URLDecoder.decode(params.get("formItemLink").toString(), "UTF-8"));

            Map tmpItemMap = new HashMap();
            for (int i = itemArr.size() - 1; i >= 0; i--) {
                JSONObject obj = itemArr.getJSONObject(i);
                JSONArray array = obj.getJSONArray("expItems");
                for (Object o : array) {
                    JSONObject json = JSONObject.parseObject(o.toString());
                    tmpItemMap.put(json.get("itemCode"), json.get("itemVal"));
                }
            }

            a:
            for (int i = itemArr.size() - 1; i >= 0; i--) {
                JSONObject obj = itemArr.getJSONObject(i);
                Long itemId = obj.getLong("itemId");
                Long itemDicId = obj.getLong("itemDicId");
                String exexExp = obj.getString("calcExp");
                if (!objRsult.containsKey(itemId.toString())) {
                    objRsult.put(itemId.toString(), "");
                }
                // 获取当前配置的项目信息，如果当前项目不是当前病种的，则跳过
                SdsQcformItemEntity linkItem = FormItemCache.me().getFormItemById(itemId);
                // 查找规则公式中括号以内的字符
                Pattern p = Pattern.compile("\\(.*?\\)");// 查找规则公式中括号以内的字符
                Matcher m = p.matcher(exexExp);
                while (m.find()) {// 遍历找到的所有括号
                    if (m.group().contains("\"")) { // 如果里面是常量，则继续下一个
                        continue;
                    }
                    // 取得关联项目代码
                    String itemCode = m.group().substring(1, m.group().length() - 1);
                    String linkVal = "";
                    if (CommonUtil.isNotEmpty(tmpItemMap.get(itemCode))) {
                        linkVal = tmpItemMap.get(itemCode).toString();
                    }
                    if (CommonUtil.isEmpty(linkVal)) {
                        continue a;
                    }
                    // 如果表达式有引号，那么是字符串比较，给项目值加上双引号
                    linkVal = "(\"" + linkVal + "\")";
                    // 将值替换表达式中项目代码
                    exexExp = exexExp.replace(m.group(), linkVal);
                }
                if (!exexExp.matches("\\{.*?\\}")) {
                    String[] expArr = exexExp.split(":", 2);
                    String subExpType_l = expArr[0];
                    String subExp_l = expArr[1];

                    long divisor = 1;
                    if (subExpType_l.contains("CALC")) {
                        switch (subExpType_l) {
                            case "CALC-h":
                                // 1小时毫秒数
                                divisor = 60 * 60 * 1000;
                                break;
                            case "CALC-m":
                                // 一分钟毫秒数
                                divisor = 60 * 1000;
                                break;
                            case "CALC-day":
                                // 一天毫秒数
                                divisor = 24 * 60 * 60 * 1000;
                                break;
                            case "CALC-month":
                                // 一个月毫秒数
                                divisor = 30l * 24l * 60l * 60l * 1000l;
                                break;
                            case "CALC-year":
                                // 一年毫秒数
                                divisor = 12l * 30l * 24l * 60l * 60l * 1000l;
                                break;
                            default:
                                break;
                        }
                        // 查找规则公式中小括号以内的值
                        // 替换关联项目的值
                        m = p.matcher(subExp_l);
                        String execExp = subExp_l;
                        while (m.find()) {
                            if ("()".equals(m.group()) || "(\"\")".equals(m.group())) {
                                execExp = execExp.replace(m.group(), "0");
                                continue;
                            }
                            String val = m.group().substring(1, m.group().length() - 1).replace("\"", "");
                            Long times = com.dhcc.sds.util.DateUtil.getTime(val);
                            int minutes = Math.toIntExact(times / divisor);
                            execExp = execExp.replace(val, String.valueOf(minutes));
                        }
                        exexExp = exexExp.replace(subExp_l, execExp);
                    }
                    exexExp = exexExp.replace(subExpType_l, "");
                } else {
                    // 查找规则公式中大括号以内的字符
                    Pattern pat3 = Pattern.compile("\\{.*?\\}");
                    // 替换关联项目的值
                    Matcher m3 = pat3.matcher(exexExp);
                    while (m3.find()) {
                        // 大括号中间的表达式
                        String subExpStr_l = m3.group().substring(1, m3.group().length() - 1);
                        String[] expArr = subExpStr_l.split(":", 2);
                        String subExpType_l = expArr[0];
                        String subExp_l = expArr[1];

                        long divisor = 1;
                        if (subExpType_l.contains("CALC")) {
                            switch (subExpType_l) {
                                case "CALC-h":
                                    // 1小时毫秒数
                                    divisor = 60 * 60 * 1000;
                                    break;
                                case "CALC-m":
                                    // 一分钟毫秒数
                                    divisor = 60 * 1000;
                                    break;
                                case "CALC-day":
                                    // 一天毫秒数
                                    divisor = 24 * 60 * 60 * 1000;
                                    break;
                                case "CALC-month":
                                    // 一个月毫秒数
                                    divisor = 30l * 24l * 60l * 60l * 1000l;
                                    break;
                                case "CALC-year":
                                    // 一年毫秒数
                                    divisor = 12l * 30l * 24l * 60l * 60l * 1000l;
                                    break;
                                default:
                                    break;
                            }
                            // 查找规则公式中小括号以内的值
                            // 替换关联项目的值
                            m = p.matcher(subExp_l);
                            String execExp = subExp_l;
                            while (m.find()) {
                                if ("()".equals(m.group()) || "(\"\")".equals(m.group())) {
                                    execExp = execExp.replace(m.group(), "0");
                                    continue;
                                }
                                String val = m.group().substring(1, m.group().length() - 1).replace("\"", "");
                                Long times = com.dhcc.sds.util.DateUtil.getTime(val);
                                int minutes = Math.toIntExact(times / divisor);
                                execExp = execExp.replace(val, String.valueOf(minutes));
                            }
                            exexExp = exexExp.replace(subExp_l, execExp);
                        }
                        exexExp = exexExp.replace(subExpStr_l, subExp_l);
                        exexExp = exexExp.replace(subExpType_l, "");
                    }
                }
                exexExp = exexExp.replace(":", "");
                if (exexExp.contains("contains")) {
                    exexExp = modifyExpression(exexExp);
                }
                // 将表达式中的大括号中括号替换为小括号，以及其他其他字符替换为可执行字符
                exexExp = exexExp.replace("{", "(").replace("}", ")");
                exexExp = exexExp.replace("[", "(").replace("]", ")");
                exexExp = exexExp.replace("contains(\"\")", "contains(\",,\")");
                exexExp = exexExp.replace("oth", "OTH").replace("def", "DEF");

                // 运行表达式结果且返回
                JexlEngine engine = new JexlEngine();
                JexlContext context = new MapContext();
                Expression expression = engine.createExpression(exexExp);
                String xRet = expression.evaluate(context).toString();
                String val = "";
                if (CommonUtil.equals(xRet, "true")) {
                    // 获取当前值域选项
                    SdsQcfitemDicEntity itemDic = sdsQcfitemDicMapper.selectById(itemDicId);
                    DictionaryEntity typeDic = dictionaryMapper.selectById(linkItem.getBtType());
                    String btType = typeDic.getDescription();
                    if (btType.contains("多选")) {
                        val += objRsult.get(itemId) + ",";
                    } else {
                        val = itemDic.getCode();
                    }
                }
                if (CommonUtil.isNotEmpty(val)) {
                    objRsult.put(itemId.toString(), val);
                }
            }
        } catch (UnsupportedEncodingException e) {
            throw new RuntimeException(e);
        }
        return objRsult;
    }

    /**
     * 查找项目的子项目及孙...孙孙项目（递归）
     */
    /*public Set<SdsQcformItemEntity> findSubItems(Long entityId, String itemCode, Set<SdsQcformItemEntity> linkItemList) {
        List<SdsQcformItemEntity> tmpList1 = FormItemCache.me().getFormItemByExp(entityId, "(" + itemCode + ")");

        for (SdsQcformItemEntity item : tmpList1) {
            if (linkItemList.contains(item)) {
                continue;
            }
            linkItemList.add(item);
            Set<SdsQcformItemEntity> tmpList2 = findSubItems(entityId, item.getBtCode(), linkItemList);
            if (tmpList2.size() > 0) {
                linkItemList.addAll(tmpList2);
            }
        }

        return linkItemList;
    }*/

    /**
     * 查找项目的子项目及孙...孙孙项目（优化实现）
     *
     * @param entityId   项目实体ID
     * @param itemCode   当前项目的代码，用于匹配子项目
     * @param initialLinkItemList 初始链接的项目列表，此集合在方法执行过程中不会被修改
     * @return 包含所有子项目的集合，包括递归找到的孙项目等
     */
    public Set<SdsQcformItemEntity> findSubItems(Long entityId, String itemCode, Set<SdsQcformItemEntity> initialLinkItemList) {
        Set<SdsQcformItemEntity> result = new HashSet<>(initialLinkItemList); // 保留初始集合内容，确保不修改原集合
        Set<SdsQcformItemEntity> visited = new HashSet<>(); // 用于记录已访问的项目，避免循环引用

        Deque<SdsQcformItemEntity> stack = new ArrayDeque<>(); // 使用栈实现广度优先搜索
        stack.addAll(FormItemCache.me().getFormItemByExp(entityId, "(" + itemCode + ")")); // 初始化栈顶为根节点的子项目

        while (!stack.isEmpty()) {
            SdsQcformItemEntity currentItem = stack.pollFirst(); // 弹出栈顶元素

            // 避免重复处理同一项目
            if (visited.contains(currentItem)) {
                continue;
            }
            visited.add(currentItem); // 标记当前项目已访问

            // 添加当前项目到结果集中，如果尚未添加
            if (!result.contains(currentItem)) {
                result.add(currentItem);

                // 获取当前项目的子项目并压入栈中，以便后续遍历
                List<SdsQcformItemEntity> children = FormItemCache.me().getFormItemByExp(entityId, "(" + currentItem.getBtCode() + ")");
                stack.addAll(children);
            }
        }

        return result;
    }

    /**
     * 计算项目的显隐结果
     *
     * @param itemObj
     * @return
     */
    public Map<String, Object> calcExpReslut(JSONObject itemObj, Map<String, Object> editMap) {

        Long itemId = Long.valueOf(itemObj.getString("itemId"));
        String triExp = StringEscapeUtils.unescapeHtml(itemObj.getString("triExp"));
        JSONArray linkItemArr = itemObj.getJSONArray("linkItem");

        Map<String, Object> resMap = new HashMap<>();
        resMap.put("itemId", itemId);
        resMap.put("itemCode", itemObj.getString("itemCode"));
        resMap.put("showFlg", "0");

        if (linkItemArr.size() == 0) {
            resMap.put("showFlg", "0");
            return resMap;
        }

        Map tmpItemMap = new HashMap();
        for (int i = linkItemArr.size() - 1; i >= 0; i--) {
            JSONObject obj = linkItemArr.getJSONObject(i);
            String itemCode = obj.getString("itemCode");
            if (editMap.get(itemCode) != null && editMap.get(itemCode).equals("0")) {
                tmpItemMap.put(itemCode, "");
            } else {
                tmpItemMap.put(itemCode, obj.get("itemVal"));
            }
        }

        // 查找规则公式中括号以内的字符
        Pattern pat1 = Pattern.compile(p1);
        // 替换关联项目的值
        Matcher m1 = pat1.matcher(triExp);
        while (m1.find()) {
            if (m1.group().contains("\"")) {// 如果里面是常量，则继续下一个
                continue;
            }
            String subItemCode = m1.group().substring(1, m1.group().length() - 1);
            String subItemVal = String.valueOf(tmpItemMap.get(subItemCode));
//            if (triExp.contains("\"")) {
            subItemVal = "(\"" + subItemVal + "\")";
//            }
            triExp = triExp.replace(m1.group(), subItemVal);
        }

        if (!triExp.matches(p3)) {
            String[] expArr = triExp.split(":", 2);
            String subExpType_l = expArr[0];
            String subExp_l = expArr[1];

            long divisor = 1;
            if (subExpType_l.contains("CALC")) {
                switch (subExpType_l) {
                    case "CALC-h":
                        // 1小时毫秒数
                        divisor = 60 * 60 * 1000;
                        break;
                    case "CALC-m":
                        // 一分钟毫秒数
                        divisor = 60 * 1000;
                        break;
                    case "CALC-day":
                        // 一天毫秒数
                        divisor = 24 * 60 * 60 * 1000;
                        break;
                    case "CALC-month":
                        // 一个月毫秒数
                        divisor = 30l * 24l * 60l * 60l * 1000l;
                        break;
                    case "CALC-year":
                        // 一年毫秒数
                        divisor = 12l * 30l * 24l * 60l * 60l * 1000l;
                        break;
                    default:
                        break;
                }
                // 查找规则公式中小括号以内的值
                // 替换关联项目的值
                m1 = pat1.matcher(subExp_l);
                String execExp = subExp_l;
                while (m1.find()) {
                    if ("()".equals(m1.group()) || "(\"\")".equals(m1.group()) || "(\"null\")".equals(m1.group())) {
                        execExp = execExp.replace(m1.group(), "0");
                        continue;
                    }
                    String val = m1.group().substring(1, m1.group().length() - 1).replace("\"", "");
                    Long times = DateUtil.getTime(val);
                    int minutes = Math.toIntExact(times / divisor);
                    execExp = execExp.replace(val, String.valueOf(minutes));
                }
                triExp = triExp.replace(subExp_l, execExp);
            }
            triExp = triExp.replace(subExpType_l, "");
        } else {

            // 查找规则公式中大括号以内的字符
            Pattern pat3 = Pattern.compile(p3);
            // 替换关联项目的值
            Matcher m3 = pat3.matcher(triExp);
            while (m3.find()) {
                // 大括号中间的表达式
                String subExpStr_l = m3.group().substring(1, m3.group().length() - 1);
                String[] expArr = subExpStr_l.split(":", 2);
                String subExpType_l = expArr[0];
                String subExp_l = expArr[1];

                long divisor = 1;
                if (subExpType_l.contains("CALC")) {
                    switch (subExpType_l) {
                        case "CALC-h":
                            // 1小时毫秒数
                            divisor = 60 * 60 * 1000;
                            break;
                        case "CALC-m":
                            // 一分钟毫秒数
                            divisor = 60 * 1000;
                            break;
                        case "CALC-day":
                            // 一天毫秒数
                            divisor = 24 * 60 * 60 * 1000;
                            break;
                        case "CALC-month":
                            // 一个月毫秒数
                            divisor = 30l * 24l * 60l * 60l * 1000l;
                            break;
                        case "CALC-year":
                            // 一年毫秒数
                            divisor = 12l * 30l * 24l * 60l * 60l * 1000l;
                            break;
                        default:
                            break;
                    }
                    // 查找规则公式中小括号以内的值
                    // 替换关联项目的值
                    m1 = pat1.matcher(subExp_l);
                    String execExp = subExp_l;
                    while (m1.find()) {
                        if ("()".equals(m1.group()) || "(\"\")".equals(m1.group()) || "(\"null\")".equals(m1.group())) {
                            execExp = execExp.replace(m1.group(), "0");
                            continue;
                        }
                        String val = m1.group().substring(1, m1.group().length() - 1).replace("\"", "");
                        Long times = DateUtil.getTime(val);
                        int minutes = Math.toIntExact(times / divisor);
                        execExp = execExp.replace(val, String.valueOf(minutes));
                    }
                    triExp = triExp.replace(subExp_l, execExp);
                }
                triExp = triExp.replace(subExpStr_l, subExp_l);
                triExp = triExp.replace(subExpType_l, "");
            }
        }
        triExp = triExp.replace(":", "");
        if (triExp.contains("contains")) {
            triExp = modifyExpression(triExp);
        }
        // 将表达式中的大括号中括号替换为小括号，以及其他其他字符替换为可执行字符
        triExp = triExp.replace("{", "(").replace("}", ")");
        triExp = triExp.replace("[", "(").replace("]", ")");
        triExp = triExp.replace("contains(\"\")", "contains(\",,\")");
        triExp = triExp.replace("oth", "OTH").replace("def", "DEF");

        ScriptEngineManager manager = new ScriptEngineManager();
        ScriptEngine engine = manager.getEngineByName("JavaScript");
        // 运算前置条件表达式
        try {
            if ((boolean) engine.eval(triExp)) {
                resMap.put("showFlg", "1");
                return resMap;
            }
        } catch (ScriptException e) {
            resMap.put("showFlg", "1");
            return resMap;
        }

        return resMap;
    }

    public String modifyExpression(String expression) {
        String aExp = expression;

        //判断表达式中有无中括号
        if (!expression.matches(p2)) {
            if (!expression.contains("contains")) {
                return aExp;
            }
            // 循环处理原始表达式中的子表达式
            String[] subStrArr = aExp.split(".contains");
            for (int ExpInd = 0; ExpInd < subStrArr.length; ExpInd++) {
                String expSub = subStrArr[ExpInd];  // 提取子表达式
                // 提取引号内的内容
                String regExp = "(\").*?(\")";
                Pattern pattern = Pattern.compile(regExp);
                Matcher matcher = pattern.matcher(expSub);
                while (matcher.find()) {
                    String group = matcher.group();
                    String result = group.substring(1, group.length() - 1);
                    result = "\"," + result + ",\"";
                    aExp = aExp.replaceFirst(group, result);
                }
            }
        } else {
            // 查找规则公式中中括号以内的字符
            Pattern pat2 = Pattern.compile(p2);
            // 替换关联项目的值
            Matcher m2 = pat2.matcher(aExp);
            while (m2.find()) {
                String subGroup = m2.group();
                if (!subGroup.contains("contains")) {
                    continue;
                }
                String tmpGroup = subGroup;
                String tmpSubFroup = subGroup.substring(1, subGroup.length() - 1);
                // 循环处理原始表达式中的子表达式
                String[] subStrArr = tmpSubFroup.split(".contains");
                for (int ExpInd = 0; ExpInd < subStrArr.length; ExpInd++) {
                    String expSub = subStrArr[ExpInd];  // 提取子表达式
                    // 提取引号内的内容
                    String regExp = "(\").*?(\")";
                    Pattern pattern = Pattern.compile(regExp);
                    Matcher matcher = pattern.matcher(expSub);
                    while (matcher.find()) {
                        String group = matcher.group();
                        String result = group.substring(1, group.length() - 1);
                        result = "\"," + result + ",\"";
                        tmpGroup = tmpGroup.replaceFirst(group, result);
                    }
                }
                aExp = aExp.replace(subGroup, tmpGroup);
            }
        }

        return aExp;
    }

    @Override
    public List<SdsQcFormItemDto> getItemInfo(Long mrListId) throws Exception {
        List<SdsQcFormItemDto> formItemList = new ArrayList<>();
        if (CommonUtil.isEmpty(mrListId)) {
            return formItemList;
        }
        // 获取入组信息
        SdsQcincaseEntity mrEntity = this.sdsQcincaseMapper.selectById(mrListId);
        // 获取表单项目
//        Map params = new HashMap();
//        params.put("entityId", mrEntity.getEntityId());
//        params.put("btIsActive", 1);
//        List<SdsQcformItemEntity> formItems = this.sdsQcformItemMapper.list(params);
        List<SdsQcformItemEntity> formItems = FormItemCache.me().getFormItemList(mrEntity.getEntityId());
        Map<String, Object> editPowerMap = new HashMap<>();
        for (SdsQcformItemEntity item : formItems) {
            // 项目id
            Long formItemId = item.getId();
            SdsQcFormItemDto itemDto = new SdsQcFormItemDto();
            // 查询项目结果值
            SdsQcfitemExecresultEntity execEntity = new SdsQcfitemExecresultEntity();
            execEntity.setInCaseId(mrListId);
            execEntity.setformItemId(formItemId);
            execEntity = this.sdsQcfitemExecresultMapper.selectOne(execEntity);
            if (CommonUtil.isNotEmpty(execEntity)) {
                String itemResult = execEntity.getItemResult();
                // 如果项目是字典类型，结果转换为描述
                if (CommonUtil.contains(item.getBtTypeDict().getDescription(), "字典")) {
                    String[] dicArr = itemResult.split(",");
                    String tmpResult = "";
                    String tmpResultText = "";
                    for (String dicCode : dicArr) {
                        SdsQcfitemDicEntity dic = new SdsQcfitemDicEntity();
                        dic.setFormItemId(formItemId);
                        dic.setCode(dicCode);
                        dic.setIsActive(1);
                        dic = this.sdsQcfitemDicMapper.selectOne(dic);
                        // 处理平台值域字典变动导致原表单数据无法上传问题
                        if (CommonUtil.isNotEmpty(dic)) {
                            tmpResult += dic.getCode() + ",";
                            tmpResultText += dic.getDesc() + ",";
                        }
                    }
                    if (CommonUtil.isNotEmpty(tmpResult)) {
                        tmpResult = tmpResult.substring(0, tmpResult.length() - 1);
                    }
                    if (CommonUtil.isNotEmpty(tmpResultText)) {
                        tmpResultText = tmpResultText.substring(0, tmpResultText.length() - 1);
                    }
                    itemDto.setExecResult(tmpResult);
                    itemDto.setExecResultText(tmpResultText);
                } else {
                    itemDto.setExecResultText(itemResult);
                    itemDto.setExecResult(itemResult);
                }
            }
            itemDto.setId(item.getId());
            // 根据前置条件，计算项目显隐属性
            Integer editPower = this.calcTriggerExp(mrListId, item, editPowerMap);
            editPowerMap.put(item.getBtCode(), editPower);
            itemDto.setEditPower(editPower);

            itemDto.setBtCode(item.getBtCode());
            itemDto.setBtDesc(item.getBtDesc());
            itemDto.setBtItemCat(item.getBtItemCat());
            itemDto.setBtItemSubCat(item.getBtItemSubCat());
            itemDto.setBtIndNo(item.getBtIndNo());
            itemDto.setBtTypeDesc(item.getBtTypeDict() != null ? item.getBtTypeDict().getDescription() : "");
            itemDto.setBtType(item.getBtTypeDict() != null ? item.getBtTypeDict().getCode() : "");
            itemDto.setBtUpTypeDesc(item.getBtUpTypeDict() != null ? item.getBtUpTypeDict().getDescription() : "");
            itemDto.setBtUpType(item.getBtUpTypeDict() != null ? item.getBtUpTypeDict().getCode() : "");
            itemDto.setBtIsActive(item.getBtIsActive());
            itemDto.setBtIsNeeded(item.getBtIsNeeded());
            itemDto.setBtTips(item.getBtTips());
            itemDto.setTriggerExp(item.getTriggerExp());
            itemDto.setCheckTiming(item.getCheckTimDict() != null ? item.getCheckTimDict().getDescription() : "");
            itemDto.setBtResume(item.getBtResume());

            formItemList.add(itemDto);
        }
        return formItemList;
    }

    @Override
    public List<SdsQcFormItemDto> getItemResult(Long mrListId) throws Exception {
        // 单病种上报表单是否显示病历溯源
        String isShowDataTrace = CdcConfigCache.me().getValueByKey("SDS", "SDIsShowSourceData", "N");

        List<SdsQcFormItemDto> formItemList = new ArrayList<>();
        if (CommonUtil.isEmpty(mrListId)) {
            return formItemList;
        }
        // 获取入组信息
        SdsQcincaseEntity mrEntity = this.sdsQcincaseMapper.selectById(mrListId);
        if (CommonUtil.isEmpty(mrEntity)) {
            return formItemList;
        }
        // 获取项目信息，包括结果值
        Map params = new HashMap();
        params.put("entityId", mrEntity.getEntityId());
        params.put("mrListId", mrListId);
        List<Map<String, Object>> itemList = sdsQcformItemMapper.getItemResult(params);
        int l = itemList.size();
        SdsQcformItemEntity formItem;
        SdsQcFormItemDto itemDto;
        int eCount = 0;
        int aCount = 0;
        int nCount = 0;
        Map<String, Object> editPowerMap = new HashMap<>();
        for (int i = 0; i < l; i++) {
            itemDto = new SdsQcFormItemDto();
            Integer editPower = 1;
            Map<String, Object> map = itemList.get(i);
            if (CommonUtil.isNotEmpty(map.get("triggerExp"))) {
                formItem = new SdsQcformItemEntity();
                formItem.setId(Long.valueOf(map.get("itemId").toString()));
                formItem.setEntityId(Long.valueOf(map.get("entityId").toString()));
                formItem.setTriggerExp(map.get("triggerExp").toString());
                // 根据前置条件，计算项目显隐属性
                editPower = this.calcTriggerExp(mrListId, formItem, editPowerMap);
            }
            itemDto.setId(Long.valueOf(map.get("itemId").toString()));
            if (CommonUtil.isNotEmpty(map.get("itemResult"))) {
                itemDto.setExecResult(map.get("itemResult").toString());
            }
            editPowerMap.put(map.get("btCode").toString(), editPower);
            itemDto.setEditPower(editPower);
            itemDto.setBtItemCat(map.get("itemCat").toString());
            itemDto.setBtItemSubCat(map.get("itemSubCat").toString());
            //记录表单展现项目填报情况的构成数量 add zhangdc
            if (Objects.equals(1, editPower)) {
                if (!StringUtils.isEmpty(map.get("itemResult"))) {
                    eCount++;
                }
                if (!StringUtils.isEmpty(map.get("itemResult")) && Objects.equals("A", map.get("execType"))) {
                    aCount++;
                }
                if (StringUtils.isEmpty(map.get("itemResult")) && Objects.equals(true, map.get("btIsNeeded"))) {
                    nCount++;
                }
            }
            //处理项目源数据
            /*if (CommonUtil.equals(isShowDataTrace,"Y") && CommonUtil.isNotEmpty(map.get("objectId"))) {
                String itemSourceData = processItemSourceData(String.valueOf(map.get("itemId")), String.valueOf(map.get("objectId")));
                if (!Objects.equals("A", map.get("execType"))) {
                    itemSourceData = "此项目数据经过人工填写或修正，系统初次采集源数据如下：\n\r系统采集：" + map.get("intValue") + "\n\r" + itemSourceData;
                }
                itemDto.setItemSourceData(itemSourceData);
            }*/

            formItemList.add(itemDto);
        }
        mrEntity.setECount(eCount);
        mrEntity.setACount(aCount);
        mrEntity.setNCount(nCount);
        this.sdsQcincaseMapper.updateById(mrEntity);

        return formItemList;
    }

    @Override
    public String getItemSourceDetail(Map<String, Object> params) {
        String itemSourceData = "查无数据";
        String mrListId = String.valueOf(params.get("mrListId"));
        String formItemId = String.valueOf(params.get("formItemId"));
        // 获取项目源数据objectId
        Wrapper wpr = new EntityWrapper<SdsQcfitemExecresultEntity>().eq("in_case_id", mrListId).eq("form_item_id", formItemId);
        SdsQcfitemExecresultEntity sdsQcfitemExecresult = sdsQcfitemExecresultService.selectOne(wpr);
        if (sdsQcfitemExecresult != null) {
            itemSourceData = processItemSourceData(formItemId, sdsQcfitemExecresult.getObjectId());
            if (!Objects.equals("A", sdsQcfitemExecresult.getExecType())) {
                itemSourceData = "此项目数据经过人工填写或修正，系统初次采集源数据如下：\n\r系统采集：" + sdsQcfitemExecresult.getInitValue() + "\n\r" + itemSourceData;
            }
        }

        return itemSourceData;
    }

    @Override
    public JSONArray getRealTimeItem(Map<String, Object> params) {
        JSONArray array = new JSONArray();
        Long entityId = Long.valueOf(params.get("entityId").toString());
        String formItemCode = params.get("formItemCode").toString();
        // 查找数据源配置中逻辑表达式含有当前项目code的项目
        List<SdsDataConfigEntity> logicItemConfig = sdsDataConfigMapper.selectList(new EntityWrapper<SdsDataConfigEntity>().like("calc_exp", "(" + formItemCode + ")").like("calc_exp", "REAL-TIME"));
        for (SdsDataConfigEntity dataConfig : logicItemConfig) {
            JSONObject obj = new JSONObject();
            // 获取当前配置的项目信息，如果当前项目不是当前病种的，则跳过
            SdsQcformItemEntity linkItem = FormItemCache.me().getFormItemById(dataConfig.getFitemId());
            if (CommonUtil.notEquals(linkItem.getEntityId(), entityId)) {
                continue;
            }
            String linkCalcExp = dataConfig.getCalcExp();
            // 查找规则公式中括号以内的字符
            Pattern p = Pattern.compile(p1);// 查找规则公式中括号以内的字符
            Matcher m = p.matcher(linkCalcExp);
            JSONArray linkArr = new JSONArray();
            while (m.find()) {// 遍历找到的所有括号
                if (m.group().contains("\"")) { // 如果里面是常量，则继续下一个
                    continue;
                }
                JSONObject linkObj = new JSONObject();
                // 取得关联项目代码
                String itemCode = m.group().substring(1, m.group().length() - 1);
                SdsQcformItemEntity formItem = FormItemCache.me().getFormItemByCode(entityId, itemCode);

                linkObj.put("itemId", formItem.getId());
                linkObj.put("itemCode", itemCode);
                linkArr.add(linkObj);
            }
            // 获取值域选项
            Wrapper<SdsQcfitemDicEntity> wrapper = new EntityWrapper<>();
            wrapper.eq("form_item_id", linkItem.getId());
            List<SdsQcfitemDicEntity> sdsQcfitemDicEntities = sdsQcfitemDicMapper.selectList(wrapper);
            obj.put("itemDicList", sdsQcfitemDicEntities);
            obj.put("itemId", linkItem.getId());
            obj.put("itemDicId", dataConfig.getFitemDicId());
            obj.put("calcExp", dataConfig.getCalcExp());
            obj.put("expItems", linkArr);
            array.add(obj);
        }
        return array;
    }

    @Override
    public JSONObject assembData(List<SdsQcFormItemDto> formItemList) {
        JSONObject dataJson = new JSONObject();
        for (SdsQcFormItemDto itemDto : formItemList) {
            String itemCode = itemDto.getBtCode();
            String itemResult = itemDto.getExecResult();
            String itemType = itemDto.getBtTypeDesc();
            String itemUpType = itemDto.getBtUpTypeDesc();
            if (CommonUtil.isEmpty(itemResult) || itemDto.getEditPower() == 0) continue;
            Object val = itemResult;
            if (CommonUtil.contains(itemType, "多选") || CommonUtil.contains(itemUpType, "数组")) {
                val = itemResult.split(",");
            } else if (CommonUtil.contains(itemType, "日期时间")) {
                if (CommonUtil.contains(itemUpType, "(时)")) {
                    val = itemResult.substring(0, 13);
                } else if (CommonUtil.contains(itemUpType, "(秒)")) {
                    val = itemResult;
                } else {
                    // 大多数精确到分
                    val = itemResult.substring(0, 16);
                }
            }
            dataJson.put(itemCode, val);
        }
        return dataJson;
    }

    @Override
    public Map<String, Object> uploadData(Long mrListId, JSONObject dataJSON) {
        Map<String, Object> map = new HashMap<>();
        SdsQcincaseEntity mrEntity = this.sdsQcincaseMapper.selectById(mrListId);
        // 获取前置机地址
        CdcLocationEntity location = new CdcLocationEntity();
        location.setXcode(String.valueOf(mrEntity.getInLocId()));
        location = cdcLocationMapper.selectOne(location);
        String sdServer;
        if (location != null) {
            sdServer = CdcConfigCache.me().getValueByKeyAndHospId("SDS", "SDserver", location.getHospitalId());
        } else {
            sdServer = CdcConfigCache.me().getValueByKey("SDS", "SDserver");
        }
        // 获取病种上报接口地址
        SdsQcentityEntity entity = this.sdsQcentityMapper.selectById(mrEntity.getEntityId());
        // 创建httpClient对象
        CloseableHttpClient client = HttpClients.createDefault();
        // 创建请求方法的实例，并指定请求URL
        String url = sdServer + entity.getUrl();
        HttpPost post = new HttpPost(url);
        post.setHeader("Content-Type", "application/json;charset=utf8");
        // 参数
        StringEntity strEntity = new StringEntity(dataJSON.toJSONString(), "UTF-8");
        post.setEntity(strEntity);
        // 调用execute,返回response
        CloseableHttpResponse response = null;
        try {
            response = client.execute(post);
            //HttpEntity responseEntity = response.getEntity();
            String str = EntityUtils.toString(response.getEntity());
            //JSONArray arr = JSONArray.parseArray(str);
            JSONObject obj = JSONObject.parseObject(str);
            String retCode = String.valueOf(obj.get("code"));
            String retMessage = "";
            if (CommonUtil.isNotEmpty(obj.get("message"))) {
                retMessage = String.valueOf(obj.get("message"));
            }
            // 将请求内容中的代码进行翻译
            String tmpMessage = "";
            if (isJson(retMessage)) {
                JSONObject msgObj = JSONObject.parseObject(retMessage);
                if (CommonUtil.isNotEmpty(msgObj)) {
                    JSONObject tmpObj = new JSONObject();
                    String errorMsg = String.valueOf(msgObj.get("errorMessage"));
                    if (CommonUtil.isNotEmpty(errorMsg)) {
                        if (isJson(errorMsg)) {
                            JSONObject subObj = JSONObject.parseObject(errorMsg);
                            tmpObj.putAll(subObj);
                        } else {
                            tmpObj.put("caseId", errorMsg);
                        }
                    } else {
                        tmpObj.putAll(msgObj);
                    }
                    for (String itemCode : tmpObj.keySet()) {
                        if (CommonUtil.isEmpty(tmpMessage)) {
                            tmpMessage = "上传错误明细：<br>";
                        }
//                    SdsQcformItemEntity itemEntity = new SdsQcformItemEntity();
//                    itemEntity.setEntityId(entity.getId());
//                    itemEntity.setBtCode(itemCode);
//                    itemEntity = sdsQcformItemMapper.selectOne(itemEntity);
                        SdsQcformItemEntity itemEntity = FormItemCache.me().getFormItemByCode(entity.getId(), itemCode);
                        String itmeDesc = "项目缺失";
                        if (CommonUtil.isNotEmpty(itemEntity)) {
                            itmeDesc = itemEntity.getBtDesc();
                        }
                        tmpMessage += itemCode + "(" + itmeDesc + "):<span style='color:red'>" + tmpObj.get(itemCode) + "</span><br>";
                    }
                }
            }
            if (CommonUtil.isNotEmpty(tmpMessage)) {
                retMessage = tmpMessage;
            }
            map.put("code", retCode);
            map.put("message", retMessage);
            // 返回信息Code为“1”，且无message信息，则说明前置机该病种为测试状态，将系统内该病种置为测试状态
            if (CommonUtil.equals(retCode, "1") && CommonUtil.isEmpty(retMessage)) {
                if (entity.getIsActive() == 1) {
                    entity.setIsActive(2);
                    entity.updateById();
                }
                if (mrEntity.getTestFlg() == 0) {
                    // 将该患者上报标记置为测试状态
                    mrEntity.setTestFlg(1);
                    mrEntity.updateById();
                }
            } else if (CommonUtil.equals(retCode, "1") && CommonUtil.isNotEmpty(retMessage)) {
                // 返回信息Code为“1”，且有message信息，则说明前置机该病种为正式状态，将系统内该病种置为正式状态
                if (entity.getIsActive() == 2) {
                    entity.setIsActive(1);
                    entity.updateById();
                }
                if (mrEntity.getTestFlg() == 1) {
                    // 将该患者上报标记置为正式状态
                    mrEntity.setTestFlg(0);
                    mrEntity.updateById();
                }
            }
        } catch (IOException e) {
            e.printStackTrace();
            map.put("code", 400);
            map.put("message", "上报错误：程序或网络请求异常！");
        } catch (Exception e) {
            e.printStackTrace();
            map.put("code", 400);
            map.put("message", "上报错误：程序或网络请求异常！");
        } finally {
            try {
                if (client != null) {
                    client.close();
                }
                if (response != null) {
                    response.close();
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        return map;
    }

    /**
     * 获取评估量表信息
     *
     * @param params
     * @return
     */
    @Override
    public Map<String, Object> getAsmtInfo(Map<String, Object> params) {
        Map<String, Object> result = new HashMap<String, Object>();
        Long asmtId = Long.valueOf(params.get("asmtId").toString());
        Long patientId = Long.valueOf(params.get("patientId").toString());

        // 获取量表条目和触发结果
        List<Map<String, Object>> asmtItems = sdsQcformItemMapper.getASMTItems(asmtId, patientId);
        for (int i = 0; i < asmtItems.size(); i++) {
            Map item = asmtItems.get(i);
            // 获取条目具体选择项
            Long itemId = Long.valueOf(item.get("itemId").toString());
            List<Map<String, Object>> asmtItemDics = sdsQcformItemMapper.getASMTItemDics(itemId);
            asmtItems.get(i).put("itemDics", asmtItemDics);
        }
        // 获取量表分值区间
        List<Map<String, Object>> asmtJudgeRange = sdsQcformItemMapper.getASMTJudgeRange(asmtId);

        result.put("asmtItems", asmtItems);
        result.put("levelRange", asmtJudgeRange);
        return result;
    }

    /**
     * 保存相关评估量表
     *
     * @param
     * @return
     */
    @Override
    public void saveAsmtInfo(Map<String, Object> params) {
        Long patientId = Long.valueOf(params.get("patientId").toString());
        Long asmtId = Long.valueOf(params.get("asmtId").toString());
        Long evalId = null;
        Float score = Float.valueOf(params.get("score").toString());
        String level = params.get("level").toString();
        JSONObject asmtObj = JSONObject.parseObject(params.get("sdsAsmtData").toString());
        Date now = new Date();
        // 更新保存评估结果
        SdcBusiEvaluationEntity evaluation = new SdcBusiEvaluationEntity();
        evaluation.setAssessmentId(asmtId);
        evaluation.setEpisodeId(patientId);
        evaluation.setScore(score);
        evaluation.setCreateDate(now);
        if (CommonUtil.isEmpty(params.get("evalId"))) {
            // 新增
            evaluation.insert();
            evalId = evaluation.getId();
        } else {
            evalId = Long.valueOf(params.get("evalId").toString());
            // 更新
            evaluation.setId(evalId);
            evaluation.updateById();
        }
        // 更新保存明细
        SdcBusiEvaluationItemEntity evaluationItem = new SdcBusiEvaluationItemEntity();
        evaluationItem.setEvaluationId(evalId);
        // 先全部删除再重新插入
        Wrapper<SdcBusiEvaluationItemEntity> eiWpr = new EntityWrapper<>();
        eiWpr.eq("evaluation_id", evalId);
        sdcBusiEvaluationItemMapper.delete(eiWpr);
        for (String s : asmtObj.keySet()) {
            evaluationItem = new SdcBusiEvaluationItemEntity();
            evaluationItem.setEvaluationId(evalId);
            evaluationItem.setAssessmentEntryId(Long.valueOf(s));
            evaluationItem.setUptateTime(now);
            evaluationItem.insert();
        }
    }

    /**
     * @param msgDetailsId
     * @param execUserId
     * @throws
     * @Description: 根据消息id处理his中的消息
     * @Title: handleHisMessage
     * @return: void
     * @author: wujiafeng
     * @date:2019年12月2日 下午5:18:14
     */
    @Override
    public void handleHisMessage(String msgDetailsId, String execUserId) {
        String backInfo = "";
        if (dhcHisInterfaceHead) {//有head验证
            DHCMessageServiceLocator dhcLocator = new DHCMessageServiceLocator();
            String execDate = null;//处理日期
            String execTime = null;//处理时间
            try {
                DHCMessageServiceSoap soap = dhcLocator.getDHCMessageServiceSoap(dhcHisCacheIp, dhcHisCachePath);
                backInfo = soap.execAll(msgDetailsId, execUserId, execDate, execTime);
            } catch (ServiceException e) {
                e.printStackTrace();
            } catch (RemoteException e) {
                e.printStackTrace();
            }
        } else {
            JaxWsDynamicClientFactory dcf = JaxWsDynamicClientFactory.newInstance();
            Client client = dcf.createClient(dhcHisCacheIp + dhcHisCachePath + "/dhcservice.DHCMessageInterface.cls?WSDL=1");
            Object[] objects = new Object[11];
            try {
                objects = client.invoke("ExecAll", msgDetailsId, execUserId, null, null);
                backInfo = objects[0].toString();
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
        logger.info("处理消息返回信息：" + backInfo);
    }

    @Override
    public String getDataByAdm(Map<String, Object> params) {
        String result = "";
        Map<String, Object> res = new HashMap<>();
        Long episodeId = Long.valueOf(params.get("episodeId").toString());
        Map<String, String> episodeMap = cdcEpisodeMapper.getSumInfoById(episodeId);
        List<CdcEprEntity> eprEntities = cdcEprMapper.selectList(new EntityWrapper<CdcEprEntity>().eq("episode_id", episodeId));
        for (CdcEprEntity cdcEprEntity : eprEntities) {
            switch (cdcEprEntity.getCode()) {
                case ("HDSD00.11.138"):
                    res.put("AdmDocName", cdcEprEntity.getValue());
                    break;
                case ("HDSD00.11.120"):
                    res.put("ClinicNur", cdcEprEntity.getValue());
                    break;
                case ("HDSD00.11.591"):
                    res.put("InHosWay", cdcEprEntity.getValue());
                    break;
                case ("HDSD00.11.585"):
                    res.put("PayType", cdcEprEntity.getValue());
                    break;
                case ("HDSD00.11.128"):
                    res.put("CheckDoc", cdcEprEntity.getValue());
                    break;
                case ("HDSD00.11.604"):
                    res.put("ReAdm31", cdcEprEntity.getValue());
                    break;
            }
        }
        //到院交通工具,默认私家车
        String resultVal = "私家车";
        Wrapper<CdcOrdexecEntity> ordexecEntityWrapper = new EntityWrapper<>();
        ordexecEntityWrapper.eq("episode_id", episodeId).eq("is_active", 1);
        List<CdcOrdexecEntity> cdcOrdexecEntities = cdcOrdexecMapper.selectList(ordexecEntityWrapper);
        for (CdcOrdexecEntity cdcOrdexecEntity : cdcOrdexecEntities) {
            CdcOrdmastEntity ordmastEntity = cdcOrdmastMapper.selectById(cdcOrdexecEntity.getOrderMastId());
            if (!StringUtils.isEmpty(ordmastEntity)) {
                if (ordmastEntity.getDescription().contains("救护车")) {
                    resultVal = "救护车";
                    break;
                }
            }
        }
        res.put("InHosTrans", resultVal);
        //todo:发病时间
        Map<String, Object> diagnosisMap = new HashMap<>();
        //上报：诊断来源-编目信息
        //CdcDictionaryEntity diagSource = dictionaryService.getMatchCtDic("SDS", "SDMatchCdcDic", "F");
        diagnosisMap.put("episodeId", episodeId);
        //diagnosisMap.put("diagSource", diagSource.getId());
        List<CdcDiagnosisEntity> cdcDiagnosisEntities = cdcDiagnosisMapper.selectDiagInfo(diagnosisMap);
        for (CdcDiagnosisEntity cdcDiagnosisEntity : cdcDiagnosisEntities) {
            String icd10 = cdcDiagnosisEntity.getIcd10();
            String description = cdcDiagnosisEntity.getDescription();
            if (Objects.equals(1, cdcDiagnosisEntity.getIsMain())) {
                //主要诊断ICD-10四位亚目编码与名称
                String icd4Str = "";
                if (icd10.length() > 4) {
                    icd4Str = icd10.substring(0, 5);
                }
                String lastChar = icd4Str.substring(icd4Str.length() - 1);
                if ("x".equals(lastChar)) {
                    icd4Str = icd4Str.substring(0, icd4Str.length() - 1);
                }
                lastChar = icd4Str.substring(icd4Str.length() - 1);
                if (".".equals(lastChar)) {
                    icd4Str = icd4Str.substring(0, icd4Str.length() - 1);
                }
                //主要诊断ICD-10六位临床扩展编码与名称
                String icd6Str = "";
                String substring = "";
                if (icd10.length() >= 8) {
                    substring = icd10.substring(7, 8);
                }
                if (Objects.equals("x", substring) && icd10.length() >= 11) {
                    icd6Str = icd10.substring(0, 11);
                } else if (!Objects.equals("x", substring) && icd10.length() >= 7) {
                    icd6Str = icd10.substring(0, 7);
                }
                res.put("M4DICD10", icd4Str);
                res.put("M6DICD10", icd6Str);
                res.put("MDignosDesc", description);
                continue;
            }
            //第一次要诊断描述
            res.put("ODICD10", cdcDiagnosisEntity.getDescription());
            break;
        }
        //CdcDictionaryEntity surgSource = dictionaryService.getMatchCtDic("SDS", "SDMatchCdcDic", "F1");
        List<CdcSurgeryEntity> surgeryEntities = cdcSurgeryMapper.selectSurgeryInfo(episodeId, null, null);
        if (null != surgeryEntities && surgeryEntities.size() > 0) {
            //获取编目手术 (第一手术默认为主手术)
            CdcSurgeryEntity cdcSurgeryEntity = surgeryEntities.get(0);
            String code = cdcSurgeryEntity.getCode();
            String description = cdcSurgeryEntity.getDescription();
            //主要手术操作栏中提取ICD-9-CM-3四位亚目编码与名称
            String icd4Str = "";
            if (code.length() > 4) {
                icd4Str = code.substring(0, 5);
            }
            String lastChar = icd4Str.substring(icd4Str.length() - 1);
            if ("x".equals(lastChar)) {
                icd4Str = icd4Str.substring(0, icd4Str.length() - 1);
            }
            lastChar = icd4Str.substring(icd4Str.length() - 1);
            if (".".equals(lastChar)) {
                icd4Str = icd4Str.substring(0, icd4Str.length() - 1);
            }
            //主要手术操作栏中提取ICD-9-CM-3六位临床扩展编码与名称
            String icd6Str = "";
            String substring = "";
            if (code.length() >= 8) {
                substring = code.substring(7, 8);
            }
            if (Objects.equals("x", substring) && code.length() >= 11) {
                icd6Str = code.substring(0, 11);
            } else if (code.length() >= 7) {
                icd6Str = code.substring(0, 7);
            }
            res.put("M4OCM3", icd4Str);
            res.put("M6OCM3", icd6Str);
            res.put("MOperDesc", description);
        }
        res.putAll(episodeMap);
        result = JSONObject.toJSONString(res);
        return result;
    }

    @Override
    public String getDataByFee(Map<String, Object> params) {
        String result = "";
        Map<String, Object> res = new HashMap<>();
        Long episodeId = Long.valueOf(params.get("episodeId").toString());
        Map param = new HashMap<>();
        param.put("episodeId", episodeId);
        Map<Object, Object> feeMap = sdsFunctionMapper.getFeeByType(param);
        for (Object key : feeMap.keySet()) {
            String feeValue = feeMap.get(key).toString();
            //处理精度，小数点后两位
            DecimalFormat df = new DecimalFormat("0.00");
            String format = df.format(Float.parseFloat(feeValue));
            res.put(key.toString(), format);
        }
        result = JSONObject.toJSONString(res);
        return result;
    }

    @Override
    public List<CdcOrdmastDto> getDataByOrder(Map<String, Object> params) {
        List<CdcOrdmastDto> res = new ArrayList<>();
        Long episodeId = Long.valueOf(params.get("episodeId").toString());
        Long mrListId = Long.valueOf(params.get("mrListId").toString());
        Long formItemId = Long.valueOf(params.get("formItemId").toString());
        //获取项目值对应的医嘱执行记录
        String valueByFormIdAndCaseId = sdsQcfitemExecresultService.getValueByFormIdAndCaseId(formItemId, mrListId);
        //获取病人数据源配置关联的医嘱信息
        //获取项目的数据源配置
        Wrapper<SdsDataConfigEntity> wrapper = new EntityWrapper<>();
        wrapper.eq("fitem_id", formItemId);
        wrapper.isNull("fitem_dic_id");
        List<SdsDataConfigEntity> configs = sdsDataConfigMapper.selectList(wrapper);
        // 如果有项目数据源配置
        if (CommonUtil.isNotEmpty(configs)) {
            for (SdsDataConfigEntity config : configs) {
                List<CdcOrdmastDto> cdcOrdmastDtos = new ArrayList<>();
                cdcOrdmastDtos = this.getOriginalOrdData(episodeId, mrListId, config);
                if (!cdcOrdmastDtos.isEmpty()) {
                    res.addAll(cdcOrdmastDtos);
                }
            }
        }
        // 如果有项目值域字典数据源配置
        List<SdsQcfitemDicEntity> itemDicList = FormItemDicCache.me().getFormItemDicList(formItemId);
        for (SdsQcfitemDicEntity itemDic : itemDicList) {
            if (CommonUtil.equals(itemDic.getCode(), "def")) {
                continue;
            }
            // 获取值域字典项数据源
            Wrapper<SdsDataConfigEntity> dicwWpr = new EntityWrapper<>();
            dicwWpr.eq("fitem_id", formItemId);
            dicwWpr.eq("fitem_dic_id", itemDic.getId());
            List<SdsDataConfigEntity> dicConfigList = sdsDataConfigMapper.selectList(dicwWpr);
            if (CommonUtil.isEmpty(dicConfigList)) {
                continue;
            }
            for (SdsDataConfigEntity config : dicConfigList) {
                List<CdcOrdmastDto> cdcOrdmastDtos = new ArrayList<>();
                cdcOrdmastDtos = this.getOriginalOrdData(episodeId, mrListId, config);
                if (!cdcOrdmastDtos.isEmpty()) {
                    res.addAll(cdcOrdmastDtos);
                }
            }
        }

        for (CdcOrdmastDto cdcOrdmastDto : res) {
            if (!StringUtils.isEmpty(cdcOrdmastDto.getPriorityId())) {
                CdcDictionaryEntity cdcDictionaryEntity = cdcDictionaryMapper.selectById(cdcOrdmastDto.getPriorityId());
                cdcOrdmastDto.setPriority(cdcDictionaryEntity.getDescription());
            } else {
                cdcOrdmastDto.setPriority("");
            }
            if (!StringUtils.isEmpty(cdcOrdmastDto.getStatusId())) {
                CdcDictionaryEntity cdcDictionaryEntity = cdcDictionaryMapper.selectById(cdcOrdmastDto.getStatusId());
                cdcOrdmastDto.setStatus(cdcDictionaryEntity.getDescription());
            } else {
                cdcOrdmastDto.setStatus("");
            }
        }

        return res;
    }

    @Override
    public List<CdcLisReportDto> getDataByLisReport(Map<String, Object> params) {
        List<CdcLisReportDto> res = new ArrayList<>();
        List<CdcLisReportDto> allLisReportDtos = new ArrayList<>();
        Long episodeId = Long.valueOf(params.get("episodeId").toString());
        Long mrListId = Long.valueOf(params.get("mrListId").toString());
        Long formItemId = Long.valueOf(params.get("formItemId").toString());

        //获取病人数据源配置关联的检验信息
        //获取项目的数据源配置
        Wrapper<SdsDataConfigEntity> wrapper = new EntityWrapper<>();
        wrapper.eq("fitem_id", formItemId);
        wrapper.isNull("fitem_dic_id");
        List<SdsDataConfigEntity> configs = sdsDataConfigMapper.selectList(wrapper);
        // 如果有项目数据源配置
        if (CommonUtil.isNotEmpty(configs)) {
            for (SdsDataConfigEntity config : configs) {
                if (StringUtils.isEmpty(config.getLinkStandId())) {
                    //标准字典为空，查询所有检验
                    allLisReportDtos = this.getOriginalLisReportData(episodeId, mrListId, config);
                    if (!allLisReportDtos.isEmpty()) {
                        res.addAll(allLisReportDtos);
                    }
                    break;
                }
                List<CdcLisReportDto> lisReportData = this.getOriginalLisReportData(episodeId, mrListId, config);
                if (!lisReportData.isEmpty()) {
                    res.addAll(lisReportData);
                }
            }
        }
        // 如果有项目值域字典数据源配置
        if (allLisReportDtos.isEmpty()) {
            List<SdsQcfitemDicEntity> itemDicList = FormItemDicCache.me().getFormItemDicList(formItemId);
            a:
            for (SdsQcfitemDicEntity itemDic : itemDicList) {
                if (CommonUtil.equals(itemDic.getCode(), "def")) {
                    continue;
                }
                // 获取值域字典项数据源
                Wrapper<SdsDataConfigEntity> dicwWpr = new EntityWrapper<>();
                dicwWpr.eq("fitem_id", formItemId);
                dicwWpr.eq("fitem_dic_id", itemDic.getId());
                List<SdsDataConfigEntity> dicConfigList = sdsDataConfigMapper.selectList(dicwWpr);
                if (CommonUtil.isEmpty(dicConfigList)) {
                    continue;
                }
                b:
                for (SdsDataConfigEntity config : dicConfigList) {
                    if (StringUtils.isEmpty(config.getLinkStandId())) {
                        //标准字典为空，查询所有检验
                        allLisReportDtos = this.getOriginalLisReportData(episodeId, mrListId, config);
                        if (!allLisReportDtos.isEmpty()) {
                            res.addAll(allLisReportDtos);
                        }
                        break a;
                    }
                    List<CdcLisReportDto> lisReportData = this.getOriginalLisReportData(episodeId, mrListId, config);
                    if (!lisReportData.isEmpty()) {
                        res.addAll(lisReportData);
                    }
                }
            }
        }

        //res = sdsFunctionMapper.selectOriginalLisReport(episodeId, null, null, null);
        for (CdcLisReportDto cdcLisReportDto : res) {
            if (!StringUtils.isEmpty(cdcLisReportDto.getReportStatusId())) {
                CdcDictionaryEntity cdcDictionaryEntity = cdcDictionaryMapper.selectById(cdcLisReportDto.getReportStatusId());
                cdcLisReportDto.setReportStatus(cdcDictionaryEntity.getDescription());
            } else {
                cdcLisReportDto.setReportStatus("");
            }
        }
        return res;
    }


    @Override
    public List<CdcLisReportDto> getDataByLisResult(Map<String, Object> params) {
        List<CdcLisReportDto> res = new ArrayList<>();
        Long episodeId = Long.valueOf(params.get("episodeId").toString());
        Long mrListId = Long.valueOf(params.get("mrListId").toString());
        Long formItemId = Long.valueOf(params.get("formItemId").toString());
        Long reportId = null;
        if (!StringUtils.isEmpty(params.get("reportId"))) {
            reportId = Long.valueOf(params.get("reportId").toString());
        }

        if (StringUtils.isEmpty(reportId)) {
            //根据数据源配置取值
            Wrapper<SdsDataConfigEntity> wrapper = new EntityWrapper<>();
            wrapper.eq("fitem_id", formItemId);
            wrapper.isNull("fitem_dic_id");
            List<SdsDataConfigEntity> configs = sdsDataConfigMapper.selectList(wrapper);
            // 如果有项目数据源配置
            if (CommonUtil.isNotEmpty(configs)) {
                for (SdsDataConfigEntity config : configs) {
                    List<CdcLisReportDto> cdcLisReportDtos = new ArrayList<>();
                    cdcLisReportDtos = this.getOriginalLisResultData(episodeId, mrListId, config);
                    if (!cdcLisReportDtos.isEmpty()) {
                        res.addAll(cdcLisReportDtos);
                    }
                }
            }
            // 如果有项目值域字典数据源配置
            List<SdsQcfitemDicEntity> itemDicList = FormItemDicCache.me().getFormItemDicList(formItemId);
            for (SdsQcfitemDicEntity itemDic : itemDicList) {
                if (CommonUtil.equals(itemDic.getCode(), "def")) {
                    continue;
                }
                // 获取值域字典项数据源
                Wrapper<SdsDataConfigEntity> dicwWpr = new EntityWrapper<>();
                dicwWpr.eq("fitem_id", formItemId);
                dicwWpr.eq("fitem_dic_id", itemDic.getId());
                List<SdsDataConfigEntity> dicConfigList = sdsDataConfigMapper.selectList(dicwWpr);
                if (CommonUtil.isEmpty(dicConfigList)) {
                    continue;
                }
                for (SdsDataConfigEntity config : dicConfigList) {
                    List<CdcLisReportDto> cdcLisReportDtos = new ArrayList<>();
                    cdcLisReportDtos = this.getOriginalLisResultData(episodeId, mrListId, config);
                    if (!cdcLisReportDtos.isEmpty()) {
                        res.addAll(cdcLisReportDtos);
                    }
                }
            }
        } else {
            //根据检验报告查询检验结果
            res = sdsFunctionMapper.selectOriginalLisResultByReportId(reportId);
        }
        return res;
    }

    @Override
    public List<CdcExaminateDto> getDataByRisReport(Map<String, Object> params) {
        List<CdcExaminateDto> res = new ArrayList<>();
        List<CdcExaminateDto> allExaminateDtos = new ArrayList<>();
        Long episodeId = Long.valueOf(params.get("episodeId").toString());
        Long mrListId = Long.valueOf(params.get("mrListId").toString());
        Long formItemId = Long.valueOf(params.get("formItemId").toString());
        //获取项目的数据源配置
        Wrapper<SdsDataConfigEntity> wrapper = new EntityWrapper<>();
        wrapper.eq("fitem_id", formItemId);
        wrapper.isNull("fitem_dic_id");
        List<SdsDataConfigEntity> configs = sdsDataConfigMapper.selectList(wrapper);
        // 如果有项目数据源配置
        if (CommonUtil.isNotEmpty(configs)) {
            for (SdsDataConfigEntity config : configs) {
                if (StringUtils.isEmpty(config.getLinkStandId())) {
                    //标准字典为空，查询所有检查
                    allExaminateDtos = this.getOriginalRisReportData(episodeId, mrListId, config);
                    if (!allExaminateDtos.isEmpty()) {
                        res.addAll(allExaminateDtos);
                    }
                    break;
                }
                List<CdcExaminateDto> risReportData = this.getOriginalRisReportData(episodeId, mrListId, config);
                if (!risReportData.isEmpty()) {
                    res.addAll(risReportData);
                }
            }
        }
        // 如果有项目值域字典数据源配置
        if (allExaminateDtos.isEmpty()) {
            List<SdsQcfitemDicEntity> itemDicList = FormItemDicCache.me().getFormItemDicList(formItemId);
            a:
            for (SdsQcfitemDicEntity itemDic : itemDicList) {
                if (CommonUtil.equals(itemDic.getCode(), "def")) {
                    continue;
                }
                // 获取值域字典项数据源
                Wrapper<SdsDataConfigEntity> dicwWpr = new EntityWrapper<>();
                dicwWpr.eq("fitem_id", formItemId);
                dicwWpr.eq("fitem_dic_id", itemDic.getId());
                List<SdsDataConfigEntity> dicConfigList = sdsDataConfigMapper.selectList(dicwWpr);
                if (CommonUtil.isEmpty(dicConfigList)) {
                    continue;
                }
                b:
                for (SdsDataConfigEntity config : dicConfigList) {
                    if (StringUtils.isEmpty(config.getLinkStandId())) {
                        //标准字典为空，查询所有检查
                        allExaminateDtos = this.getOriginalRisReportData(episodeId, mrListId, config);
                        if (!allExaminateDtos.isEmpty()) {
                            res.addAll(allExaminateDtos);
                        }
                        break a;
                    }
                    List<CdcExaminateDto> cdcExaminateDtos = this.getOriginalRisReportData(episodeId, mrListId, config);
                    if (!cdcExaminateDtos.isEmpty()) {
                        res.addAll(cdcExaminateDtos);
                    }
                }
            }
        }
        for (CdcExaminateDto cdcExaminateDto : res) {
            if (!StringUtils.isEmpty(cdcExaminateDto.getReportStatusId())) {
                CdcDictionaryEntity cdcDictionaryEntity = cdcDictionaryMapper.selectById(cdcExaminateDto.getReportStatusId());
                cdcExaminateDto.setReportStatus(cdcDictionaryEntity.getDescription());
            } else {
                cdcExaminateDto.setReportStatus("");
            }
        }
        return res;
    }

    private List<CdcExaminateDto> getOriginalRisReportData(Long episodeId, Long mrListId, SdsDataConfigEntity config) {
        List<CdcExaminateDto> res = new ArrayList<>();
        String sqlStr = this.calcGetExecTiming(episodeId, config.getGetTiming());
        if (!StringUtils.isEmpty(config.getLinkStandId())) {
            // 查询标准项所有关联医嘱
            List<Long> ordMastList = sdsStandDicMatchMapper.selectMatchOrderId(config.getLinkStandId());
            // 查找子节点关联医嘱
            //查找子节点
            List<Long> dicChildrenIds = sdsStandDicService.getRootChildren(config.getLinkStandId());
            for (Long dicChildrenId : dicChildrenIds) {
                ordMastList.addAll(sdsStandDicMatchMapper.selectMatchOrderId(dicChildrenId));
            }
            if (ordMastList.isEmpty()) {
                return res;
            }
            // 去重
            Set<Long> ordMastSet = new HashSet(ordMastList);
            ordMastList = new ArrayList(ordMastSet);
            res = sdsFunctionMapper.selectOriginalExaminate(episodeId, null, ordMastList, sqlStr);
            if (!res.isEmpty()) {
                return res;
            }
        } else {
            // 未配置标准项，查询患者所有检查项目
            res = sdsFunctionMapper.selectOriginalExaminate(episodeId, null, new ArrayList<>(), sqlStr);
        }
        return res;
    }

    @Override
    public List<CdcNurDto> getDataByNur(Map<String, Object> params) {
        List<CdcNurDto> cdcNurDtos = new ArrayList<>();
        return cdcNurDtos;
    }

    /**
     * 2024/1/12新增填报处的自动评估  保存自动评估结果
     *
     * @param params
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void saveAIAsmtInfo(Map<String, Object> params) {
        //1.先判断填报项中该评估项是否有分值 即是否有历史评估
        Integer isScored = sdcBusiEvaluationMapper.isScored(params);
        //2.1有历史评估 则不需要自动评估  无需操作
        if (isScored == 0) {
            //2.2没有历史评估 则需要自动评估
            Long patientId = Long.valueOf(params.get("patientId").toString());
            Long asmtId = Long.valueOf(params.get("asmtId").toString());
            Long fitemId = Long.valueOf(params.get("fitemId").toString());
            String timeCode = dictionaryMapper.getTimeCode(fitemId);
            String orderSql = null;
            if ("InHosp".equals(timeCode)) {
                //入院首次
                orderSql = "asc";
            } else if ("LastInHosp".equals(timeCode)) {
                //住院末次
                orderSql = "desc";
            }
            // 3 看t_sdc_busi_evaluation_his表有没有保存过，有则更新当条,没有则新增
            List<Map<String, Object>> asmtItems = sdsToolSdkMapper.getASMTItems(asmtId);
            for (int i = 0; i < asmtItems.size(); i++) {

                Map item = asmtItems.get(i);
                // 获取条目具体选择项
                Long itemId = Long.valueOf(item.get("itemId").toString());
                List<Map<String, Object>> asmtItemDics = sdsToolSdkMapper.getASMTItemDics(itemId);
                for (Map<String, Object> asmtItemDic : asmtItemDics) {
                    //获取计算公式formula 判断规则
                    if (asmtItemDic.containsKey("formula")) {
                        Object formula = asmtItemDic.get("formula");
                        if (!StringUtils.isEmpty(formula) && formula != null) {
                            String formulaStr = formula.toString();
                            Map<String, Object> res = (Map) isdsStandRuleCalService.handleRuleExpressions(formulaStr, patientId, orderSql);
                            Long dicId = (Long) asmtItemDic.get("dicId");
                            SdcBusiEvaluationHisEntity sdcBusiEvaluationHisEntity = new SdcBusiEvaluationHisEntity();
                            sdcBusiEvaluationHisEntity.setEpisodeId(patientId);
                            sdcBusiEvaluationHisEntity.setAssessmentEntryId(dicId);
                            sdcBusiEvaluationHisEntity.setAssessmentId(asmtId);
                            int auto = 1;
                            sdcBusiEvaluationHisEntity.setAuto(auto);
                            int comeFrom = 1;
                            sdcBusiEvaluationHisEntity.setComeFrom(comeFrom);
                            String modifyUserName = "系统";
                            sdcBusiEvaluationHisEntity.setEvalDocName(modifyUserName);
                            SdcBusiEvaluationHisEntity sdcBusiEvaluationHisEntity1 = sdcBusiEvaluationHisMapper.selectOne(sdcBusiEvaluationHisEntity);
                            boolean bool = (boolean) res.get("bool");
                            if (bool) {
                                //匹配评估规则  保存自动评估结果
                                sdcBusiEvaluationHisEntity.setResult("");
                                sdcBusiEvaluationHisEntity.setEvalDate(new Date());
                                String keyWordsfrom = "";
                                String keyWordsfroms = "";
                                //拼接规则如   基本信息：年龄≥65岁
                                List<String> ruleCodeList = (List<String>) res.get("ruleCodeList");
                                if (!CollectionUtils.isEmpty(ruleCodeList)) {
                                    for (int i1 = 0; i1 < ruleCodeList.size(); i1++) {
                                        Wrapper<SdsStandRuleBaseEntity> wrapper = new EntityWrapper<>();
                                        wrapper.eq("rule_code", ruleCodeList.get(i1));
                                        SdsStandRuleBaseEntity sdsStandRuleBaseEntity = iSdsStandRuleBaseService.selectOne(wrapper);
                                        String ruleType = sdsStandRuleBaseEntity.getRuleType();
                                        String ruleDesc = sdsStandRuleBaseEntity.getRuleDesc();
                                        if (!StringUtils.isEmpty(ruleType) && !StringUtils.isEmpty(ruleDesc)) {
                                            keyWordsfrom = ruleType + ":" + ruleDesc;
                                            if (ruleCodeList.size() > 1 && i1 < ruleCodeList.size() - 1) {
                                                keyWordsfroms += keyWordsfrom + "且";
                                            }
                                            if (i1 == ruleCodeList.size() - 1) {
                                                keyWordsfroms += keyWordsfrom;
                                            }
                                        }
                                    }
                                }
                                sdcBusiEvaluationHisEntity.setKeyWordsfrom(keyWordsfroms);
                                SdcBaseAssessmenentryEntity sdcBaseAssessmenentryEntity = sdcBaseAssessmenentryMapper.selectById(dicId);
                                String score1 = sdcBaseAssessmenentryEntity.getScore();
                                Float score;
                                if (score1.contains("分")) {
                                    score = Float.parseFloat(score1.replace("分", ""));
                                } else {
                                    score = Float.parseFloat(score1);
                                }
                                sdcBusiEvaluationHisEntity.setScore(score);

                                if (sdcBusiEvaluationHisEntity1 != null) {
                                    //删除并新增
                                    sdcBusiEvaluationHisEntity1.deleteById();
                                    sdcBusiEvaluationHisEntity.insert();
                                } else {
                                    //新增
                                    sdcBusiEvaluationHisEntity.insert();
                                }
                            } else {
                                //不匹配规则，可能是信息变动，需要查该评估项是否已经存表、有则删除
                                if (sdcBusiEvaluationHisEntity1 != null) {
                                    sdcBusiEvaluationHisEntity1.deleteById();
                                }
                            }
                        }
                    }
                }
            }
        }
    }

    /**
     * 2024/1/12新增填报处的自动评估   返回自动评估结果
     *
     * @param params
     * @return
     */
    @Override
    public Object getAIAsmtInfo(Map<String, Object> params) {
        Object result = null;
        //当填报项中该评估项有分值 即有历史评估  则返回空
        Integer isScored = sdcBusiEvaluationMapper.isScored(params);
        if (isScored > 0) {
            return result;
        }
        List<SdcBusiEvaluationHisEntity> sdcBusiEvaluationHisEntities = sdcBusiEvaluationHisMapper.selectList(new EntityWrapper<SdcBusiEvaluationHisEntity>()
                .eq("episode_id", params.get("patientId"))
                .eq("assessment_id", params.get("asmtId"))
                .eq("auto", 1)
                .eq("come_from", 1));
        if (sdcBusiEvaluationHisEntities.size() > 0) {
            result = sdcBusiEvaluationHisEntities;
        }
        return result;
    }

    private List<CdcLisReportDto> getOriginalLisResultData(Long episodeId, Long mrListId, SdsDataConfigEntity config) {
        List<CdcLisReportDto> res = new ArrayList<>();
        String valueTimeSql = getLabResultValueTimeSql(episodeId, config.getGetTiming());
        if (!StringUtils.isEmpty(config.getLinkStandId())) {
            //查找关联检查项目
            Map<String, Object> param = new HashMap<String, Object>();
            // 查询标准项所有关联医嘱
            param.put("dicId", config.getLinkStandId());
            List<Long> labItemIds = sdsStandDicMatchMapper.selectMatchLabIds(param);
            List<Map<String, Object>> list = new ArrayList<>();
            if (!labItemIds.isEmpty()) {
                res = sdsFunctionMapper.selectOriginalLisResult(episodeId, null, labItemIds, valueTimeSql);
            }
        }

        return res;
    }

    private List<CdcOrdmastDto> getOriginalOrdData(Long episodeId, Long mrListId, SdsDataConfigEntity config) {
        List<CdcOrdmastDto> res = new ArrayList<>();
        SdsStandSourceEntity source = sdsStandSourceMapper.selectById(config.getDsId());
        if (!StringUtils.isEmpty(source)) {
            // 采集时机, 获取取值条件
            String sqlStr = this.calcGetExecTiming(episodeId, config.getGetTiming());
            if (!StringUtils.isEmpty(config.getLinkStandId())) {
                // 查询标准项关联医嘱
                List<Long> ordMastList = sdsStandDicMatchMapper.selectMatchOrderId(config.getLinkStandId());
                //查找子节点
                List<Long> dicChildrenIds = sdsStandDicService.getRootChildren(config.getLinkStandId());
                for (Long dicChildrenId : dicChildrenIds) {
                    ordMastList.addAll(sdsStandDicMatchMapper.selectMatchOrderId(dicChildrenId));
                }
                if (ordMastList.isEmpty()) {
                    return res;
                }
                // 去重
                Set<Long> ordMastSet = new HashSet(ordMastList);
                ordMastList = new ArrayList(ordMastSet);
                res = sdsFunctionMapper.selectOriginalOrdExec(episodeId, null, ordMastList, sqlStr);
            }
        }
        return res;
    }

    private List<CdcLisReportDto> getOriginalLisReportData(Long episodeId, Long mrListId, SdsDataConfigEntity config) {
        List<CdcLisReportDto> res = new ArrayList<>();
        String valueTimeSql = getLabResultValueTimeSql(episodeId, config.getGetTiming());
        if (!StringUtils.isEmpty(config.getLinkStandId())) {
            // 查询标准项所有关联医嘱
            List<Long> labIds = sdsStandDicMatchMapper.selectMatchOrderId(config.getLinkStandId());
            if (!labIds.isEmpty()) {
                res = sdsFunctionMapper.selectOriginalLisReport(episodeId, null, labIds, valueTimeSql);
            }
            if (CommonUtil.isNotEmpty(res)) {
                return res;
            }
        } else {
            res = sdsFunctionMapper.selectOriginalLisReport(episodeId, null, null, null);
            if (CommonUtil.isNotEmpty(res)) {
                return res;
            }
        }
        return res;
    }


    private String calcGetExecTiming(Long episodeId, Long valueTime) {
        String sqlStr = "";
        String filterSqlByDate = "AND oe.bus_order_priority_id <> ${priorityId} AND (oe.first_exec_date BETWEEN str_to_date('${sTime}','%Y-%m-%d %H:%i:%s') AND str_to_date('${eTime}', '%Y-%m-%d %H:%i:%s') OR oe.start_date BETWEEN str_to_date('${sTime}','%Y-%m-%d %H:%i:%s') AND str_to_date('${eTime}', '%Y-%m-%d %H:%i:%s'))";
        String filterSqlByAsc = "AND oe.bus_order_priority_id <> ${priorityId} ORDER BY IF(ISNULL(oe.first_exec_date),1,0) ${seqType}, oe.start_date ${seqType}";
        String filterSqlByDesc = "AND oe.bus_order_priority_id <> ${priorityId} ORDER BY IF(ISNULL(oe.last_exec_date),0,1) ${seqType}, oe.start_date ${seqType}";
        String filterSqlByPriority = "AND oe.bus_order_priority_id = ${priorityId} ORDER BY oe.start_date ${seqType}";
        String filterSqlByInstruc = "AND oe.bus_order_instruc_id = ${instrucId} ORDER BY oe.start_date ${seqType}";
        String seqType = "";
        Long priorityId = 0L;
        Long instrucId = 0L;
        Long tmpTime = 0L;
        String fTime = "";
        String tTime = "";

        // 出院带药 bus_order_priority:OUT
        CdcDictionaryEntity cdcDictionaryEntity = cdcDictionaryService.queryByTypeCodeAndCode("OrdData", "bus_order_priority", "OUT");
        if (!StringUtils.isEmpty(cdcDictionaryEntity)) {
            priorityId = cdcDictionaryEntity.getId();
        }

        // 如果没有配置采集时机，默认入院首次
        if (CommonUtil.isEmpty(valueTime)) {
            Map<String, Object> map = new HashMap<>();
            map.put("seqType", "ASC");
            map.put("priorityId", priorityId);
            StrSubstitutor strSubstitutor = new StrSubstitutor(map);
            sqlStr = strSubstitutor.replace(filterSqlByAsc);
            return sqlStr;
        }
        // 获取采集时间描述
        DictionaryEntity getTimingDic = dictionaryMapper.selectById(valueTime);
        String getType = getTimingDic.getCode();
        // 如果采集时机包含手术，则先取手术开始、结束时间
        if (getType.contains("Oper")) {
            Wrapper<CdcSurgeryEntity> operWpr = new EntityWrapper<>();
            operWpr.eq("episode_id", episodeId).eq("is_active", 1).orderBy("start_date");
            List<CdcSurgeryEntity> operList = cdcSurgeryMapper.selectList(operWpr);
            if (operList.size() == 0) {
                return "";
            }
            // 只取首次手术
            Date startDate = com.dhcc.core.framework.util.DateUtil.parse("1900-01-01 00:00:00");
            Date endDate = com.dhcc.core.framework.util.DateUtil.parse("1900-01-01 00:00:00");
            switch (getType) {
                case "BfOper":
                    for (CdcSurgeryEntity oper : operList) {
                        if (oper.getStartDate() != null || oper.getEndDate() != null) {
                            startDate = oper.getStartDate();
                            break;
                        }
                    }
                    // 术前，默认手术前0.5-1小时
                    tmpTime = startDate.getTime();
                    fTime = com.dhcc.core.framework.util.DateUtil.getTime(new Date(tmpTime - 3600 * 1000));
                    tTime = com.dhcc.core.framework.util.DateUtil.getTime(new Date(tmpTime - 1800 * 1000));
                    sqlStr = filterSqlByDate;
                    break;
                case "InOper":
                    for (CdcSurgeryEntity oper : operList) {
                        if (oper.getStartDate() != null && oper.getEndDate() != null) {
                            startDate = oper.getStartDate();
                            endDate = oper.getEndDate();
                            break;
                        }
                    }
                    // 术中
                    fTime = com.dhcc.core.framework.util.DateUtil.getTime(startDate);
                    tTime = com.dhcc.core.framework.util.DateUtil.getTime(endDate);
                    sqlStr = filterSqlByDate;
                    break;
                case "AfOper":
                    for (CdcSurgeryEntity oper : operList) {
                        if (oper.getStartDate() != null || oper.getEndDate() != null) {
                            endDate = oper.getEndDate();
                            break;
                        }
                    }
                    // 术后，默认手术后72小时
                    tmpTime = endDate.getTime();
                    fTime = com.dhcc.core.framework.util.DateUtil.getTime(endDate);
                    tTime = com.dhcc.core.framework.util.DateUtil.getTime(new Date(tmpTime + 3 * 24 * 3600 * 1000));
                    sqlStr = filterSqlByDate;
                    break;
                case "AllOper":
                    for (CdcSurgeryEntity oper : operList) {
                        if (oper.getStartDate() != null || oper.getEndDate() != null) {
                            startDate = oper.getStartDate();
                            endDate = oper.getEndDate();
                            break;
                        }
                    }
                    //围术期
                    tmpTime = startDate.getTime();
                    fTime = com.dhcc.core.framework.util.DateUtil.getTime(new Date(tmpTime - 3600 * 1000));
                    tmpTime = endDate.getTime();
                    tTime = com.dhcc.core.framework.util.DateUtil.getTime(new Date(tmpTime + 3 * 24 * 3600 * 1000));
                    sqlStr = filterSqlByDate;
                    break;
                case "WithOperRoom":
                    // 带手术室 bus_order_instruc:1
                    CdcDictionaryEntity cdcDictionaryEntity2 = cdcDictionaryService.queryByTypeCodeAndCode("OrdData", "bus_order_instruc", "1");
                    if (!StringUtils.isEmpty(cdcDictionaryEntity2)) {
                        instrucId = cdcDictionaryEntity2.getId();
                    }
                    seqType = "ASC";
                    sqlStr = filterSqlByInstruc;
                    break;
            }
        } else {
            // 获取就诊时间
            CdcEpisodeEntity admObj = cdcEpisodeMapper.selectById(episodeId);
            Date admDate = admObj.getAdmDate();
            Date dishDate = admObj.getDishDate();
            switch (getType) {
                case "Emergency":
                    // 急诊, 默认早于入院时间
                    tmpTime = admDate.getTime();
                    fTime = com.dhcc.core.framework.util.DateUtil.getTime(new Date(tmpTime - 24 * 3600 * 1000));
                    tTime = com.dhcc.core.framework.util.DateUtil.getTime(new Date(tmpTime));
                    sqlStr = filterSqlByDate;
                    break;
                case "LastInHosp":
                    // 住院末次
                    seqType = "DESC";
                    sqlStr = filterSqlByDesc;
                    break;
                case "EMR-Inhos24":
                    // 急诊/入院24小时
                    tmpTime = admDate.getTime();
                    fTime = com.dhcc.core.framework.util.DateUtil.getTime(admDate);
                    tTime = com.dhcc.core.framework.util.DateUtil.getTime(new Date(tmpTime + 24 * 3600 * 1000));
                    sqlStr = filterSqlByDate;
                    break;
                case "DishHosMedi":
                    seqType = "ASC";
                    sqlStr = filterSqlByPriority;
                    break;
                case "LongOrder":
                    // 长期医嘱 bus_order_priority:S
                    CdcDictionaryEntity cdcDictionaryEntity1 = cdcDictionaryService.queryByTypeCodeAndCode("OrdData", "bus_order_priority", "S");
                    if (!StringUtils.isEmpty(cdcDictionaryEntity1)) {
                        priorityId = cdcDictionaryEntity1.getId();
                    }
                    seqType = "ASC";
                    sqlStr = filterSqlByPriority;
                    break;
                case "DurHosp":
                    // 住院期间 医嘱日期范围为住院期间
                    fTime = com.dhcc.core.framework.util.DateUtil.getTime(admDate);
                    tTime = com.dhcc.core.framework.util.DateUtil.getTime(dishDate);
                    sqlStr = filterSqlByDate;
                    break;
                default:
                    // 默认入院首次
                    seqType = "ASC";
                    sqlStr = filterSqlByAsc;
                    break;
            }
        }
        Map<String, Object> map = new HashMap<>();
        map.put("sTime", fTime);
        map.put("eTime", tTime);
        map.put("seqType", seqType);
        map.put("priorityId", priorityId);
        map.put("instrucId", instrucId);
        StrSubstitutor strSubstitutor = new StrSubstitutor(map);
        sqlStr = strSubstitutor.replace(sqlStr);
        return sqlStr;
    }

    private String getLabResultValueTimeSql(Long episodeId, Long valueTime) {
        String sqlStr = "";
        String filterSqlByDate = "AND n.report_date BETWEEN str_to_date('${sTime}','%Y-%m-%d %H:%i:%s') AND str_to_date('${eTime}', '%Y-%m-%d %H:%i:%s')";
        String filterSqlBySort = " ORDER BY n.report_date ${seqType}";
        String seqType = "";
        Long tmpTime = 0L;
        String fTime = "";
        String tTime = "";

        Map<String, Object> map = new HashMap<>();
        map.put("seqType", "ASC");
        // 如果没有配置采集时机，默认入院首次
        if (CommonUtil.isEmpty(valueTime)) {
            StrSubstitutor strSubstitutor = new StrSubstitutor(map);
            sqlStr = strSubstitutor.replace(filterSqlBySort);
            return sqlStr;
        }
        // 获取采集时间描述
        DictionaryEntity getTimingDic = dictionaryMapper.selectById(valueTime);
        String getType = getTimingDic.getCode();
        // 如果采集时机包含手术，则先取手术开始、结束时间
        if (getType.contains("Oper")) {
            Wrapper<CdcSurgeryEntity> operWpr = new EntityWrapper<>();
            operWpr.eq("episode_id", episodeId).eq("is_active", 1).orderBy("start_date");
            List<CdcSurgeryEntity> operList = cdcSurgeryMapper.selectList(operWpr);
            if (operList.size() == 0) {
                return "";
            }
            // 只取首次手术
            Date startDate = com.dhcc.core.framework.util.DateUtil.parse("1900-01-01 00:00:00");
            Date endDate = com.dhcc.core.framework.util.DateUtil.parse("1900-01-01 00:00:00");
            switch (getType) {
                case "BfOper":
                    for (CdcSurgeryEntity oper : operList) {
                        if (oper.getStartDate() != null || oper.getEndDate() != null) {
                            startDate = oper.getStartDate();
                            break;
                        }
                    }
                    // 术前，默认手术前0.5-1小时
                    tmpTime = startDate.getTime();
                    fTime = com.dhcc.core.framework.util.DateUtil.getTime(new Date(tmpTime - 3600 * 1000));
                    tTime = com.dhcc.core.framework.util.DateUtil.getTime(new Date(tmpTime - 1800 * 1000));
                    sqlStr = filterSqlByDate;
                    break;
                case "InOper":
                    for (CdcSurgeryEntity oper : operList) {
                        if (oper.getStartDate() != null && oper.getEndDate() != null) {
                            startDate = oper.getStartDate();
                            endDate = oper.getEndDate();
                            break;
                        }
                    }
                    // 术中
                    fTime = com.dhcc.core.framework.util.DateUtil.getTime(startDate);
                    tTime = com.dhcc.core.framework.util.DateUtil.getTime(endDate);
                    sqlStr = filterSqlByDate;
                    break;
                case "AfOper":
                    for (CdcSurgeryEntity oper : operList) {
                        if (oper.getStartDate() != null || oper.getEndDate() != null) {
                            endDate = oper.getEndDate();
                            break;
                        }
                    }
                    // 术后，默认手术后72小时
                    tmpTime = endDate.getTime();
                    fTime = com.dhcc.core.framework.util.DateUtil.getTime(endDate);
                    tTime = com.dhcc.core.framework.util.DateUtil.getTime(new Date(tmpTime + 3 * 24 * 3600 * 1000));
                    sqlStr = filterSqlByDate;
                    break;
                case "AllOper":
                    for (CdcSurgeryEntity oper : operList) {
                        if (oper.getStartDate() != null || oper.getEndDate() != null) {
                            startDate = oper.getStartDate();
                            endDate = oper.getEndDate();
                            break;
                        }
                    }
                    //围术期
                    tmpTime = startDate.getTime();
                    fTime = com.dhcc.core.framework.util.DateUtil.getTime(new Date(tmpTime - 3600 * 1000));
                    tmpTime = endDate.getTime();
                    tTime = com.dhcc.core.framework.util.DateUtil.getTime(new Date(tmpTime + 3 * 24 * 3600 * 1000));
                    sqlStr = filterSqlByDate;
                    break;
            }
        } else {
            // 获取就诊时间
            CdcEpisodeEntity admObj = cdcEpisodeMapper.selectById(episodeId);
            Date admDate = admObj.getAdmDate();
            Date dishDate = admObj.getDishDate();
            switch (getType) {
                case "Emergency":
                    // 急诊, 默认早于入院时间
                    tmpTime = admDate.getTime();
                    fTime = com.dhcc.core.framework.util.DateUtil.getTime(new Date(tmpTime - 24 * 3600 * 1000));
                    tTime = com.dhcc.core.framework.util.DateUtil.getTime(new Date(tmpTime));
                    sqlStr = filterSqlByDate;
                    break;
                case "LastInHosp":
                    // 住院末次
                    map.put("seqType", "DESC");
                    sqlStr = filterSqlBySort;
                    break;
                case "EMR-Inhos24":
                    // 急诊/入院24小时
                    tmpTime = admDate.getTime();
                    fTime = com.dhcc.core.framework.util.DateUtil.getTime(admDate);
                    tTime = com.dhcc.core.framework.util.DateUtil.getTime(new Date(tmpTime + 24 * 3600 * 1000));
                    sqlStr = filterSqlByDate;
                    break;
                case "DurHosp":
                    // 住院期间 医嘱日期范围为住院期间
                    fTime = com.dhcc.core.framework.util.DateUtil.getTime(admDate);
                    tTime = com.dhcc.core.framework.util.DateUtil.getTime(dishDate);
                    sqlStr = filterSqlByDate;
                    break;
                default:
                    // 默认入院首次
                    map.put("seqType", "ASC");
                    sqlStr = filterSqlBySort;
                    break;
            }
        }
        map.put("sTime", fTime);
        map.put("eTime", tTime);
        StrSubstitutor strSubstitutor = new StrSubstitutor(map);
        sqlStr = strSubstitutor.replace(sqlStr);
        return sqlStr;
    }

    public static boolean isJson(String content) {
        if (CommonUtil.isEmpty(content)) {
            return false;
        }
        try {
            JSONObject.parseObject(content);
            return true;
        } catch (Exception e) {
            return false;
        }
    }

    private String processItemSourceData(String itemId, String itemSourceData) {
        String itemSourceDataNew = "";
        if (CommonUtil.isNotEmpty(itemSourceData)) {
            String[] objIdArr = itemSourceData.split(";");
            for (String objSourceDate : objIdArr) {
                String[] sourceArr = objSourceDate.split("_");
                String sourceCode = sourceArr[0];
                String sourceName = sourceArr.length > 1 ? sourceArr[1] : "";
                if (CommonUtil.isNotEmpty(sourceName)) {
                    cn.hutool.json.JSONArray jsonArray = JSONUtil.parseArray(sourceName);
                    for (Object objId : jsonArray) {
                        itemSourceDataNew += getItemSourceData(itemId, sourceCode, objId.toString());
                    }
                } else {
                    if (CommonUtil.equals(sourceCode, "default")) {
                        itemSourceDataNew = "默认项设置";
                    } else if (CommonUtil.isNotEmpty(sourceCode)) {
                        itemSourceDataNew = "无数据";
                    }
                }
            }
        }

        return itemSourceDataNew;
    }

    private String getItemSourceData(String itemId, String sourceCode, String objId) {
        String sourceStr = "";
        switch (sourceCode) {
            case "Episode":
                sourceStr = this.processEpisodeData(itemId, objId);
                break;
            case "Ordexec":
                sourceStr = this.processOrdExecData(itemId, objId);
                break;
            case "Diagnosis":
                sourceStr = this.processDiagnosisData(itemId, objId);
                break;
            case "EmrInfo":
                sourceStr = this.processEmrInfoData(itemId, objId);
                break;
            case "EmrStructInfo":
                sourceStr = this.processEmrStructData(sourceCode, itemId, objId);
                break;
            case "EmrOperInfo":
            case "Operate":
                sourceStr = this.processOperData(itemId, objId);
                break;
            case "EprBaseInfo":
                sourceStr = this.processEprBaseData(itemId, objId);
                break;
            case "Ris":
                sourceStr = this.processExamData(itemId, objId);
                break;
            case "ExamStructInfo":
                sourceStr = this.processExamStructData(sourceCode, itemId, objId);
                break;
            case "LisResult":
                sourceStr = this.processLisResultData(itemId, objId);
                break;
            case "LisReport":
                sourceStr = this.processLisReportData(itemId, objId);
                break;
            case "LisVisit":
                sourceStr = this.processLisVisitData(itemId, objId);
                break;
            case "Sign":
                sourceStr = this.processSignData(itemId, objId);
                break;
            case "EprFeeInfo":
                sourceStr = this.processFeeData(itemId, objId);
                break;
            case "NurRecord":
                sourceStr = this.processNurRecordData(itemId, objId);
                break;
            default:
                break;
        }
        return sourceStr;
    }
    private String processFeeData(String itemId, String objId) {
        String sourceStr = "病案首页费用";
        return sourceStr;
    }

    private String processSignData(String itemId, String objId) {
        String sourceStr = "";
        String signCode = "";
        String signName = "";
        String signValue = "";
        String signTime = "";
        CdcSignEntity cdcSignEntity = cdcSignMapper.selectById(objId);
        if (cdcSignEntity != null) {
            signCode = cdcSignEntity.getCode();
            signName = cdcSignEntity.getDescription();
            signValue = cdcSignEntity.getValue();
            if (CommonUtil.isNotEmpty(cdcSignEntity.getCheckDate())) {
                signTime = com.dhcc.core.framework.util.DateUtil.getTime(cdcSignEntity.getCheckDate());
            }
        }
        sourceStr += "<div style=\"padding:2px;\">";
        sourceStr += "<div><span style=\"font-weight: bold;\">体征代码：</span>" + signCode + "<div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">体征名称：</span>" + signName + "<div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">体征值：</span><span style=\"color: #77DD77\">" + signValue + "</span><div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">录入时间：</span>" + signTime + "<div>";
        sourceStr += "</div>";
        return sourceStr;
    }

    private String processLisVisitData(String itemId, String objId) {
        String sourceStr = "";
        String labOrderName = "";
        String specimenType = "";
        String collectionDate = "";
        // 获取送检信息
        CdcLabVisitEntity labVisit = cdcLabVisitMapper.selectById(objId);
        if (labVisit != null) {
            specimenType = labVisit.getSpecimen();
            if (CommonUtil.isNotEmpty(labVisit.getColDate())) {
                collectionDate = com.dhcc.core.framework.util.DateUtil.getTime(labVisit.getColDate());
            }
            // 获取检验医嘱
            List<CdcLabSetEntity> labSetList = cdcLabSetMapper.selectList(new EntityWrapper<CdcLabSetEntity>().eq("lab_visit_id", labVisit.getId()));
            for (CdcLabSetEntity labSet : labSetList) {
                Long labOrderId = labSet.getCtLabOrderId();
                // 获取检验医嘱信息
                CdcLabOrderEntity labOrder = cdcLabOrderMapper.selectById(labOrderId);
                if (labOrder != null) {
                    labOrderName += labOrder.getDescription() + ";";
                }
            }
        }
        sourceStr += "<div style=\"padding:2px;\">";
        sourceStr += "<div><span style=\"font-weight: bold;\">检验医嘱：</span>" + labOrderName + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">送检标本：</span>" + specimenType + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">采样日期：</span>" + collectionDate + "</div>";
        sourceStr += "</div>";
        return sourceStr;
    }

    private String processLisReportData(String itemId, String objId) {
        String sourceStr = "";
        String labOrderName = "";
        String specimenType = "";
        String collectionDate = "";
        String labReportDate = "";
        // 获取检验报告信息
        CdcLabReportEntity labReport = cdcLabReportMapper.selectById(objId);
        if (labReport != null) {
            if (CommonUtil.isNotEmpty(labReport.getReportDate())) {
                labReportDate = com.dhcc.core.framework.util.DateUtil.getTime(labReport.getReportDate());
            }
            // 获取送检信息
            CdcLabVisitEntity labVisit = cdcLabVisitMapper.selectById(labReport.getLabVisitId());
            if (labVisit != null) {
                specimenType = labVisit.getSpecimen();
                if (CommonUtil.isNotEmpty(labVisit.getColDate())) {
                    collectionDate = com.dhcc.core.framework.util.DateUtil.getTime(labVisit.getColDate());
                }
                // 获取检验医嘱
                List<CdcLabSetEntity> labSetList = cdcLabSetMapper.selectList(new EntityWrapper<CdcLabSetEntity>().eq("lab_visit_id", labVisit.getId()));
                for (CdcLabSetEntity labSet : labSetList) {
                    Long labOrderId = labSet.getCtLabOrderId();
                    // 获取检验医嘱信息
                    CdcLabOrderEntity labOrder = cdcLabOrderMapper.selectById(labOrderId);
                    if (labOrder != null) {
                        labOrderName += labOrder.getDescription() + ";";
                    }
                }
            }
        }
        sourceStr += "<div style=\"padding:2px;\">";
        sourceStr += "<div><span style=\"font-weight: bold;\">检验医嘱：</span>" + labOrderName + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">送检标本：</span>" + specimenType + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">采样日期：</span>" + collectionDate + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">报告日期：</span>" + labReportDate + "</div>";
        sourceStr += "</div>";
        return sourceStr;
    }

    private String processLisResultData(String itemId, String objId) {
        String sourceStr = "";
        String labOrderName = "";
        String specimenType = "";
        String collectionDate = "";
        String labReportDate = "";
        String labItemName = "";
        String labItemValue = "";
        String labItemUnit = "";
        String labItemRange = "";
        String abnormalDesc = "";
        CdcLabResultEntity cdcLabResultEntity = cdcLabResultMapper.selectById(objId);
        if (cdcLabResultEntity != null) {
            // 获取检验项目信息
            CdcLabItemEntity labItem = cdcLabItemMapper.selectById(cdcLabResultEntity.getLabItemId());
            if (labItem != null) {
                labItemName = labItem.getDescription();
                labItemValue = cdcLabResultEntity.getResult();
                labItemUnit = cdcLabResultEntity.getResultUnit();
                labItemRange = cdcLabResultEntity.getResultRange();
                abnormalDesc = cdcLabResultEntity.getAbnormalDesc();
                // 获取检验报告信息
                CdcLabReportEntity labReport = cdcLabReportMapper.selectById(cdcLabResultEntity.getLabReportId());
                if (labReport != null) {
                    if (CommonUtil.isNotEmpty(labReport.getReportDate())) {
                        labReportDate = com.dhcc.core.framework.util.DateUtil.getTime(labReport.getReportDate());
                    }
                    // 获取送检信息
                    CdcLabVisitEntity labVisit = cdcLabVisitMapper.selectById(labReport.getLabVisitId());
                    if (labVisit != null) {
                        specimenType = labVisit.getSpecimen();
                        if (CommonUtil.isNotEmpty(labVisit.getColDate())) {
                            collectionDate = com.dhcc.core.framework.util.DateUtil.getTime(labVisit.getColDate());
                        }
                        // 获取检验医嘱
                        List<CdcLabSetEntity> labSetList = cdcLabSetMapper.selectList(new EntityWrapper<CdcLabSetEntity>().eq("lab_visit_id", labVisit.getId()));
                        for (CdcLabSetEntity labSet : labSetList) {
                            Long labOrderId = labSet.getCtLabOrderId();
                            // 获取检验医嘱信息
                            CdcLabOrderEntity labOrder = cdcLabOrderMapper.selectById(labOrderId);
                            if (labOrder != null) {
                                labOrderName += labOrder.getDescription() + ";";
                            }
                        }
                    }
                }
            }
        }

        sourceStr += "<div style=\"padding:2px;\">";
        sourceStr += "<div><span style=\"font-weight: bold;\">检验医嘱：</span>" + labOrderName + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">送检标本：</span>" + specimenType + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">采样日期：</span>" + collectionDate + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">报告日期：</span>" + labReportDate + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">检验项目：</span>" + labItemName + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">检验结果：</span>" + labItemValue + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">异常提示：</span>" + abnormalDesc + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">结果单位：</span>" + labItemUnit + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">参考范围：</span>" + labItemRange + "</div>";
        sourceStr += "</div>";
        return sourceStr;
    }

    private String processExamData(String itemId, String objId) {
        String sourceStr = "";
        String examName = "";
        String examDesc = "";
        String examDiag = "";
        String examRepDate = "";
        // 获取检查报告原文
        CdcExaminateEntity cdcExaminate = cdcExaminateMapper.selectById(objId);
        if (cdcExaminate != null) {
            examName = cdcExaminate.getDescription();
            examDesc = cdcExaminate.getExamDesc();
            examDiag = cdcExaminate.getResultDesc();
            if (CommonUtil.isNotEmpty(cdcExaminate.getRepDate())) {
                examRepDate = com.dhcc.core.framework.util.DateUtil.getTime(cdcExaminate.getRepDate());
            }
        }
        // 获取值域字典
        List<SdsQcfitemDicEntity> dicList = FormItemDicCache.me().getFormItemDicList(Long.valueOf(itemId));
        for (SdsQcfitemDicEntity itemDic : dicList) {
            String keywords = itemDic.getKeyword();
            if (CommonUtil.isNotEmpty(keywords)) {
                String regex = keywords;
                Pattern pattern = Pattern.compile(regex);
                Matcher matcher = pattern.matcher(examDiag);
                Matcher matcher2 = pattern.matcher(examDesc);
                examDiag = matcher.replaceAll("<span style=\"color:red;\">$0</span>");
                examDesc = matcher2.replaceAll("<span style=\"color:red;\">$0</span>");
            } else {
                String dicDesc = itemDic.getDesc();
                examDiag = examDiag.replace(dicDesc, "<span style=\"color:red);\">" + dicDesc + "</span>");
                examDesc = examDesc.replace(dicDesc, "<span style=\"color:red;\">" + dicDesc + "</span>");
            }
        }
        sourceStr += "<div style=\"padding:2px;\">";
        sourceStr += "<div><span style=\"font-weight: bold;\">检查名称：</span>" + examName + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">检查所见：</span>" + examDesc + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">诊断意见：</span>" + examDiag + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">报告日期：</span>" + examRepDate + "</div>";
        sourceStr += "</div>";
        return sourceStr;
    }

    private String processExamStructData(String sourceCode, String itemId, String objId) {
        String sourceStr = "";
        String examName = "";
        String examDesc = "";
        String examDiag = "";
        String examRepDate = "";
        // 获取检查报告原文
        CdcExaminateEntity cdcExaminate = cdcExaminateMapper.selectById(objId);
        if (cdcExaminate != null) {
            examName = cdcExaminate.getDescription();
            examDesc = cdcExaminate.getExamDesc();
            examDiag = cdcExaminate.getResultDesc();
            if (CommonUtil.isNotEmpty(cdcExaminate.getRepDate())) {
                examRepDate = com.dhcc.core.framework.util.DateUtil.getTime(cdcExaminate.getRepDate());
            }
        }

        // 获取项目数据源配置
        Wrapper<SdsDataConfigEntity> wrapper = new EntityWrapper<>();
        wrapper.eq("fitem_id", itemId);
        List<SdsDataConfigEntity> configs = sdsDataConfigMapper.selectList(wrapper);
        for (SdsDataConfigEntity config : configs) {
            // 获取数据源
            SdsStandSourceEntity source = sdsStandSourceMapper.selectById(config.getDsId());
            if (CommonUtil.isNotEmpty(source)) {
                SdsStandSourceEntity parentSourceEntity = sdsStandSourceMapper.selectById(source.getParentId());
                if (CommonUtil.isNotEmpty(parentSourceEntity)) {
                    String methodName = parentSourceEntity.getSourceCode();
                    if (CommonUtil.equals(sourceCode, methodName)) {
                        // 获取标准字典配置
                        //查找标准字典关联的对照参数
                        List<SdsStandDicMatchParamEntity> dicMatchParams = sdsStandDicMatchParamMapper.selectList(new EntityWrapper<SdsStandDicMatchParamEntity>()
                                .eq("dic_id", config.getLinkStandId()));
                        for (SdsStandDicMatchParamEntity dicMatchParam : dicMatchParams) {
                            String param = dicMatchParam.getCompareContent();
                            String[] split1 = param.split("#");
                            String name = split1[0];
                            if (!CommonUtil.contains(examDiag, name) && !CommonUtil.contains(examDesc, name)) {
                                continue;
                            }
                            String replaceChar = "<span style=\"color:red;\">" + name + "</span>";
                            examDiag = examDiag.replace(name, replaceChar);
                            examDesc = examDesc.replace(name, replaceChar);
                        }

                    }
                }
            }
        }
        sourceStr += "<div style=\"padding:2px;\">";
        sourceStr += "<div><span style=\"font-weight: bold;\">检查名称：</span>" + examName + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">检查所见：</span>" + examDesc + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">诊断意见：</span>" + examDiag + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">报告日期：</span>" + examRepDate + "</div>";
        sourceStr += "</div>";
        return sourceStr;
    }

    private String processEprBaseData(String itemId, String objId) {
        String sourceStr = "";
        CdcEprEntity cdcEpr = cdcEprMapper.selectById(objId);
        if (cdcEpr != null) {
            sourceStr = cdcEpr.getDescription() + ": " + cdcEpr.getValue();
        }
        return sourceStr;
    }

    private String processEpisodeData(String itemId, String objId) {
        String sourceStr = "";
        String name = "";
        String admLocDesc = "";
        String admWardDesc = "";
        String mrNo = "";
        String sex = "";
        String age = "";
        String idCard = "";
        String address = "";
        String birthDate = "";
        String admissionDate = "";
        String dischargeDate = "";
        String admDocName = "";
        String oeDate = "";
        String admDays = "";
        CdcEpisodeEntity episodeEntity = cdcEpisodeMapper.selectById(objId);
        if (episodeEntity != null) {
            name = episodeEntity.getName();
            idCard = episodeEntity.getCardValue();
            address = episodeEntity.getNativePlace();
            admLocDesc = episodeEntity.getAdmLocDesc();
            admWardDesc = episodeEntity.getAdmWardDesc();
            admDocName = episodeEntity.getAdmDoctorName();
            mrNo = episodeEntity.getMrNum();
            sex = episodeEntity.getGender();
            age = episodeEntity.getAge();
            if (CommonUtil.isNotEmpty(episodeEntity.getBirthdate())) {
                birthDate = com.dhcc.core.framework.util.DateUtil.getTime(episodeEntity.getBirthdate());
            }
            if (CommonUtil.isNotEmpty(episodeEntity.getAdmDate())) {
                admissionDate = com.dhcc.core.framework.util.DateUtil.getTime(episodeEntity.getAdmDate());
            }
            if (CommonUtil.isNotEmpty(episodeEntity.getDishDate())) {
                dischargeDate = com.dhcc.core.framework.util.DateUtil.getTime(episodeEntity.getDishDate());
            }
            if (CommonUtil.isNotEmpty(episodeEntity.getOeDate())) {
                oeDate = com.dhcc.core.framework.util.DateUtil.getTime(episodeEntity.getOeDate());
            }
        }
        sourceStr += "<div style=\"padding:2px;\">";
        sourceStr += "<div><span style=\"font-weight: bold;\">姓名：</span>" + name + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">性别：</span>" + sex + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">年龄：</span>" + age + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">住院号：</span>" + mrNo + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">身份证号：</span>" + idCard + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">住址：</span>" + address + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">出生日期：</span>" + birthDate + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">门急诊日期：</span>" + oeDate + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">入院日期：</span>" + admissionDate + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">住院科室：</span>" + admLocDesc + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">住院病区：</span>" + admWardDesc + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">主管医生：</span>" + admDocName + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">出院日期：</span>" + dischargeDate + "</div>";
        sourceStr += "</div>";
        return sourceStr;
    }

    private String processOperData(String itemId, String objId) {
        String sourceStr = "";
        String operIcd = "";
        String operName = "";
        String operStartDate = "";
        String operEndDate = "";
        // 获取手术
        CdcSurgeryEntity cdcSurgery = cdcSurgeryMapper.selectById(objId);
        if (cdcSurgery != null) {
            operIcd = cdcSurgery.getCode();
            operName = cdcSurgery.getDescription();
            if (CommonUtil.isNotEmpty(cdcSurgery.getStartDate())) {
                operStartDate = com.dhcc.core.framework.util.DateUtil.getTime(cdcSurgery.getStartDate());
            }
            if (CommonUtil.isNotEmpty(cdcSurgery.getEndDate())) {
                operEndDate = com.dhcc.core.framework.util.DateUtil.getTime(cdcSurgery.getEndDate());
            }
        }
        sourceStr += "<div style=\"padding:2px;\">";
        sourceStr += "<div><span style=\"font-weight: bold;\">手术编码：</span>" + operIcd + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">手术名称：</span>" + operName + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">手术时间：</span>" + operStartDate + (CommonUtil.isNotEmpty(operStartDate) ? "~" : "") + operEndDate + "</div>";
        sourceStr += "</div>";
        return sourceStr;
    }

    private String processEmrInfoData(String itemId, String objId) {
        String sourceStr = "";
        String emrTitle = "";
        String emrSubTitle = "";
        String emrContent = "";
        String emrTime = "";
        // 获取病历记录
        CdcEmrEntity cdcEmrInfo = cdcEmrMapper.selectById(objId);
        if (cdcEmrInfo != null) {
            emrTitle = cdcEmrInfo.getTitle();
            emrSubTitle = cdcEmrInfo.getSubTitle();
            emrContent = cdcEmrInfo.getContent();
            if (CommonUtil.isNotEmpty(cdcEmrInfo.getEmrDate())) {
                emrTime = com.dhcc.core.framework.util.DateUtil.getTime(cdcEmrInfo.getEmrDate());
            }
        }
        // 获取值域字典
        List<SdsQcfitemDicEntity> dicList = FormItemDicCache.me().getFormItemDicList(Long.valueOf(itemId));
        for (SdsQcfitemDicEntity itemDic : dicList) {
            String keywords = itemDic.getKeyword();
            if (CommonUtil.isNotEmpty(keywords)) {
                String regex = keywords;
                Pattern pattern = Pattern.compile(regex);
                Matcher matcher = pattern.matcher(emrContent);
                emrContent = matcher.replaceAll("<span style=\"color:red;\">$0</span>");
            } else {
                String dicDesc = itemDic.getDesc();
                emrContent = emrContent.replace(dicDesc, "<span style=\"color:red);\">" + dicDesc + "</span>");
            }
        }
        sourceStr += "<div style=\"padding:2px;\">";
        sourceStr += "<div><span style=\"font-weight: bold;\">病历标题：</span>" + emrTitle + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">病历摘要：</span>" + emrSubTitle + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">病历内容：</span>" + emrContent + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">病历时间：</span>" + emrTime + "</div>";
        sourceStr += "</div>";
        return sourceStr;

    }

    private String processEmrStructData(String sourceCode, String itemId, String objId) {
        String sourceStr = "";
        String emrTitle = "";
        String emrSubTitle = "";
        String emrContent = "";
        String emrTime = "";
        // 获取病历记录
        CdcEmrEntity cdcEmrInfo = cdcEmrMapper.selectById(objId);
        if (cdcEmrInfo != null) {
            emrTitle = cdcEmrInfo.getTitle();
            emrSubTitle = cdcEmrInfo.getSubTitle();
            emrContent = cdcEmrInfo.getContent();
            if (CommonUtil.isNotEmpty(cdcEmrInfo.getEmrDate())) {
                emrTime = com.dhcc.core.framework.util.DateUtil.getTime(cdcEmrInfo.getEmrDate());
            }
        }
        // 获取项目数据源配置
        Wrapper<SdsDataConfigEntity> wrapper = new EntityWrapper<>();
        wrapper.eq("fitem_id", itemId);
        List<SdsDataConfigEntity> configs = sdsDataConfigMapper.selectList(wrapper);
        for (SdsDataConfigEntity config : configs) {
            // 获取数据源
            SdsStandSourceEntity source = sdsStandSourceMapper.selectById(config.getDsId());
            if (CommonUtil.isNotEmpty(source)) {
                SdsStandSourceEntity parentSourceEntity = sdsStandSourceMapper.selectById(source.getParentId());
                if (CommonUtil.isNotEmpty(parentSourceEntity)) {
                    String methodName = parentSourceEntity.getSourceCode();
                    if (CommonUtil.equals(sourceCode, methodName)) {
                        // 获取标准字典配置
                        //查找标准字典关联的对照参数
                        List<SdsStandDicMatchParamEntity> dicMatchParams = sdsStandDicMatchParamMapper.selectList(new EntityWrapper<SdsStandDicMatchParamEntity>()
                                .eq("dic_id", config.getLinkStandId()));
                        for (SdsStandDicMatchParamEntity dicMatchParam : dicMatchParams) {
                            String param = dicMatchParam.getCompareContent();
                            String[] split1 = param.split("#");
                            String name = split1[0];
                            if (!CommonUtil.contains(emrContent, name)) {
                                continue;
                            }
                            String replaceChar = "<span style=\"color:red;\">" + name + "</span>";
                            emrContent = emrContent.replace(name, replaceChar);
                        }
                    }
                }
            }
        }

        sourceStr += "<div style=\"padding:2px;\">";
        sourceStr += "<div><span style=\"font-weight: bold;\">病历标题：</span>" + emrTitle + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">病历摘要：</span>" + emrSubTitle + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">病历内容：</span>" + emrContent + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">病历时间：</span>" + emrTime + "</div>";
        sourceStr += "</div>";
        return sourceStr;

    }

    private String processDiagnosisData(String itemId, String objId) {
        String sourceStr = "";
        String diagnosisIcd = "";
        String diagnosisName = "";
        String diagnosisTime = "";
        String diagnosisType = "";
        // 获取诊断记录
        CdcDiagnosisEntity cdcDiagnosis = cdcDiagnosisMapper.selectById(objId);
        if (CommonUtil.isNotEmpty(cdcDiagnosis)) {
            if (cdcDiagnosis != null) {
                diagnosisIcd = cdcDiagnosis.getIcd10();
                diagnosisName = cdcDiagnosis.getDescription();
                diagnosisType = cdcDiagnosis.getIsMain() == 1 ? "主要诊断" : "次要诊断";
                if (CommonUtil.isNotEmpty(cdcDiagnosis.getDiagDate())) {
                    diagnosisTime = com.dhcc.core.framework.util.DateUtil.getTime(cdcDiagnosis.getDiagDate());
                }
            }
        }
        sourceStr += "<div style=\"padding:2px;\">";
        sourceStr += "<div><span style=\"font-weight: bold;\">诊断类型：</span>" + diagnosisType + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">诊断编码：</span>" + diagnosisIcd + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">诊断名称：</span>" + diagnosisName + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">诊断时间：</span>" + diagnosisTime + "</div>";
        sourceStr += "</div>";
        return sourceStr;
    }

    private String processOrdExecData(String itemId, String objId) {
        String sourceStr = "";
        String orderName = "";
        String priorityType = "";
        String instrucType = "";
        String orderTime = "";
        String firstExecTime = "";
        String lastExecTime = "";
        // 获取医嘱记录
        CdcOrdexecEntity cdcOrdexec = cdcOrdexecMapper.selectById(objId);
        if (CommonUtil.isNotEmpty(cdcOrdexec)) {
            // 获取医嘱项信息
            CdcOrdmastEntity cdcOrdmast = cdcOrdmastMapper.selectById(cdcOrdexec.getOrderMastId());
            // 医嘱项名称
            if (CommonUtil.isNotEmpty(cdcOrdmast)) {
                orderName = cdcOrdmast.getDescription();
            }
            // 开具时间
            if (CommonUtil.isNotEmpty(cdcOrdexec.getOrderDate())) {
                orderTime = com.dhcc.core.framework.util.DateUtil.getTime(cdcOrdexec.getOrderDate());
            }
            // 首次执行时间
            if (CommonUtil.isNotEmpty(cdcOrdexec.getFirstExecDate())) {
                firstExecTime = com.dhcc.core.framework.util.DateUtil.getTime(cdcOrdexec.getFirstExecDate());
            }
            // 末次执行时间
            if (CommonUtil.isNotEmpty(cdcOrdexec.getLastExecDate())) {
                lastExecTime = com.dhcc.core.framework.util.DateUtil.getTime(cdcOrdexec.getLastExecDate());
            }
            // 给药途径
            if (CommonUtil.isNotEmpty(cdcOrdexec.getBusOrderInstrucId())) {
                CdcDictionaryEntity instrucEntity = cdcDictionaryMapper.selectById(cdcOrdexec.getBusOrderInstrucId());
                if (instrucEntity != null) {
                    instrucType = instrucEntity.getDescription();
                }
            }
            // 医嘱类型
            if (CommonUtil.isNotEmpty(cdcOrdexec.getBusOrderPriorityId())) {
                CdcDictionaryEntity priorityEntity = cdcDictionaryMapper.selectById(cdcOrdexec.getBusOrderPriorityId());
                if (priorityEntity != null) {
                    priorityType = priorityEntity.getDescription();
                }
            }
        }
        sourceStr += "<div style=\"padding:2px;\">";
        sourceStr += "<div><span style=\"font-weight: bold;\">医嘱名称：</span>" + orderName + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">医嘱类型：</span>" + priorityType + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">给药途径：</span>" + instrucType + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">医嘱时间：</span>" + orderTime + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">首次执行时间：</span>" + firstExecTime + "</div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">最后执行时间：</span>" + lastExecTime + "</div>";
        sourceStr += "</div>";

        return sourceStr;
    }

    private String processNurRecordData(String itemId, String objId) {
        String sourceStr = "";
        String docName = "";
        String itemName = "";
        String itemValue = "";
        String itemTime = "";
        CdcNurEntity cdcNurEntity = cdcNurMapper.selectById(objId);
        if (cdcNurEntity != null) {
            docName = cdcNurEntity.getDocName();
            itemName = cdcNurEntity.getDescription();
            itemValue = cdcNurEntity.getContent();
            if (CommonUtil.isNotEmpty(cdcNurEntity.getNurDate())) {
                itemTime = com.dhcc.core.framework.util.DateUtil.getTime(cdcNurEntity.getNurDate());
            }
        }
        sourceStr += "<div style=\"padding:2px;\">";
        sourceStr += "<div><span style=\"font-weight: bold;\">护理文书：</span>" + docName + "<div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">项目名称：</span>" + itemName + "<div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">项目值：</span><span style=\"color: #77DD77\">" + itemValue + "</span><div>";
        sourceStr += "<div><span style=\"font-weight: bold;\">录入时间：</span>" + itemTime + "<div>";
        sourceStr += "</div>";
        return sourceStr;
    }

    @Override
    public String reEnroll(Map<String, Object> params) {
        String newEntityName = "";
        // 获取当前排除的病种信息
        String mrListId = String.valueOf(params.get("mrListId"));
        SdsQcincaseEntity excludeCase = sdsQcincaseMapper.selectById(mrListId);
        if (excludeCase != null) {
            // 获取排除病种信息
            Long excludeEntityId = excludeCase.getEntityId();
            try {
                Map<String, Object> resultMap = checkSDByAdm(excludeCase.getEpisodeId(), excludeEntityId);
                if (CommonUtil.isNotEmpty(resultMap)) {
                    newEntityName = resultMap.get("entityDesc").toString();
                    Long newMrListId = resultMap.get("mrListId") == null ? 0 : Long.parseLong(resultMap.get("mrListId").toString());
                    //执行自动取值
                    sdsQcfitemExecresultService.execItemResult(newMrListId);
                    //表单填充率
                    try {
                        this.getItemResult(newMrListId);
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                }
            } catch (Exception e) {
                e.printStackTrace();
                return "";
            }
        }
        return newEntityName;
    }

    /**
     * 根据就诊号进行重新入组规则筛查
     *
     * @param aEpisodeID
     * @param excludeEntityId
     * @return
     */
    public Map<String, Object> checkSDByAdm(Long aEpisodeID, Long excludeEntityId) throws Exception {
        Map<String, Object> resultMap = new HashMap<>();
        String entityDesc = "";
        Date inDate = null;
        //通过就诊id获取就诊对象
        CdcEpisodeEntity cdcEpisodeEntity = cdcEpisodeMapper.selectById(aEpisodeID);
        //获取病种信息
        SdsQcentityEntity excludeEntity = QcEntityCache.me().getQcEntityById(excludeEntityId);
        if (!StringUtils.isEmpty(cdcEpisodeEntity)) {
            Long mrListID = null;
            Date nowDate = new Date();
            //遍历已经开展的质控病种
            Wrapper<SdsQcentityEntity> wpr = new EntityWrapper<>();
            wpr.ne("is_active", 0).gt("ind_no", excludeEntity.getIndNo()).orderBy("ind_no"); // 非作废病种且按照排序码排序
            List<SdsQcentityEntity> qcentityEntities = sdsQcentityMapper.selectList(wpr);
            a:
            for (SdsQcentityEntity sdsQcentityEntity : qcentityEntities) {
                if (!StringUtils.isEmpty(mrListID)) {
                    //已入病种，退出判断
                    break a;
                }
                //按照关联科室过滤患者
                String linkDept = sdsQcentityEntity.getLinkDept();
                if (CommonUtil.isNotEmpty(linkDept)) {
                    Wrapper<CdcTransferEntity> transferOutCCU = new EntityWrapper<>();
                    transferOutCCU.eq("episode_id", aEpisodeID).eq("is_active", 1);
                    List<CdcTransferEntity> cdcTransferList = cdcTransferMapper.selectList(transferOutCCU);
                    boolean deptFlag = false;
                    b:
                    for (String deptCode : linkDept.split(",")) {
                        for (CdcTransferEntity cdcTransferEntity : cdcTransferList) {
                            if (!StringUtils.isEmpty(cdcTransferEntity.getTranBedId())) {
                                //只检索转科记录
                                continue;
                            }
                            CdcLocationEntity locationEntity = cdcLocationMapper.selectById(cdcTransferEntity.getTranLocId());
                            if (!StringUtils.isEmpty(locationEntity)) {
                                if (CommonUtil.equals(deptCode, locationEntity.getXcode())) {
                                    deptFlag = true;
                                    break b;
                                }
                            }
                        }
                    }
                    if (!deptFlag) {
                        continue;
                    }
                }

                //防止排除的病种再次筛查
                Wrapper<SdsQcincaseEntity> wrapper = new EntityWrapper<>();
                wrapper.eq("episode_id", aEpisodeID)
                        .eq("entity_id", sdsQcentityEntity.getId())
                        .eq("state", "O");
                List<SdsQcincaseEntity> list = sdsQcincaseMapper.selectList(wrapper);
                if (!list.isEmpty()) {
                    continue;
                }
                Map<String, Object> map2 = new HashMap<>();
                map2.put("entityId", sdsQcentityEntity.getId());
                List<SdsQcentityRuleEntity> qcentityRuleEntities = sdsQcentityRuleMapper.list(map2);
                //准入规则
                List<SdsQcentityRuleEntity> admits = new ArrayList<>();
                //排除规则
                List<SdsQcentityRuleEntity> exclude = new ArrayList<>();
                for (SdsQcentityRuleEntity sdsQcentityRuleEntity : qcentityRuleEntities) {
                    if ((!Objects.equals(1, sdsQcentityRuleEntity.getIsActive()))
                            || (Objects.equals(1, sdsQcentityRuleEntity.getIsOnly()))) {
                        continue;
                    }
                    if (Objects.equals("1", sdsQcentityRuleEntity.getRuleType())) {
                        admits.add(sdsQcentityRuleEntity);
                    } else {
                        exclude.add(sdsQcentityRuleEntity);
                    }
                }
                //有准入配置，才进行入组判断
                String ret = "";
                String ruleId = "";
                if (!admits.isEmpty()) {
                    //Param2:判断且伴为同一组的准入规则，排序相同的为同一组
                    //String param2 = sdsQcentityRuleEntity.getParam2();
                    //按Param2进行分组
                    Map<String, List<SdsQcentityRuleEntity>> collect = admits.stream().collect(Collectors.groupingBy(p -> p.getParam2() == null ? "" : p.getParam2(), Collectors.toList()));
                    b:
                    for (String param2 : collect.keySet()) {
                        List<SdsQcentityRuleEntity> sdsQcentityRuleEntities = collect.get(param2);
                        //每一组ruleId重置
                        ruleId = "";
                        for (SdsQcentityRuleEntity sdsQcentityRuleEntity : sdsQcentityRuleEntities) {
                            ret = "N";
                            SdsExpressEntity sdsExpressEntity = sdsExpressMapper.selectById(sdsQcentityRuleEntity.getExpressId());
                            if (!StringUtils.isEmpty(sdsExpressEntity)) {
                                Class c = Class.forName("com.dhcc.sds.base.function.GetEntrySrv");
                                GetEntrySrv getEntrySrv = SpringContextHolder.getBean("getEntrySrv");
                                Method method = c.getMethod(sdsExpressEntity.getExpress(), Long.class, String.class);
                                ret = (String) method.invoke(getEntrySrv, aEpisodeID, sdsQcentityRuleEntity.getParam());
                                if (!Objects.equals("Y", ret)) {
                                    continue b;
                                } else {
                                    //记录ruleId
                                    ruleId += sdsQcentityRuleEntity.getId() + ",";
                                }
                            }
                        }
                        if (Objects.equals("Y", ret)) {
                            //多个准入，并行满足一个跳出
                            break b;
                        }
                    }
                    DefaultTransactionDefinition definition = new DefaultTransactionDefinition();
                    definition.setPropagationBehavior(TransactionDefinition.PROPAGATION_REQUIRED);
                    TransactionStatus transactionStatus = platformTransactionManager.getTransaction(definition);
                    try {
                        if (Objects.equals("Y", ret)) {
                            //如果满足第一准入条件，直接进入单病种列表
                            SdsQcincaseEntity sdsQcincaseEntity = new SdsQcincaseEntity();
                            sdsQcincaseEntity.setEpisodeId(aEpisodeID);
                            sdsQcincaseEntity.setEntityId(sdsQcentityEntity.getId());
                            sdsQcincaseEntity.setInUserId(cdcEpisodeEntity.getAdmDoctorId());
                            sdsQcincaseEntity.setInLocId(cdcEpisodeEntity.getAdmLocId());
                            sdsQcincaseEntity.setInWardId(cdcEpisodeEntity.getAdmWardId());
                            sdsQcincaseEntity.setInDate(nowDate);
                            sdsQcincaseEntity.setInTime(nowDate);
                            sdsQcincaseEntity.setState("I");
                            sdsQcincaseEntity.setGroupStatus("SysRec");
                            sdsQcincaseEntity.setFillingStatus("NotFilled");
                            sdsQcincaseEntity.setReportStatus("NotUp");
                            sdsQcincaseEntity.setIntheMoment("D");

                            Integer insert = sdsQcincaseMapper.insert(sdsQcincaseEntity);

                            if (insert == 1) {
                                //增加病历状态记录
                                SdsQcincaseOperlogEntity sdsQcincaseOperlogEntity = new SdsQcincaseOperlogEntity();
                                sdsQcincaseOperlogEntity.setInCaseId(sdsQcincaseEntity.getId());
                                sdsQcincaseOperlogEntity.setOperState("I");
                                sdsQcincaseOperlogEntity.setOperUser("系统");
                                sdsQcincaseOperlogEntity.setOperDate(nowDate);
                                sdsQcincaseOperlogEntity.setOperReason(ruleId);
                                Integer insert1 = sdsQcincaseOperlogMapper.insert(sdsQcincaseOperlogEntity);
                                if (insert1 == 1) {
                                    mrListID = sdsQcincaseEntity.getId();
                                    entityDesc = sdsQcentityEntity.getBtDesc();
                                    inDate = sdsQcincaseEntity.getInDate();
                                    resultMap.put("entityDesc", entityDesc);
                                    resultMap.put("mrListId", sdsQcincaseEntity.getId());
                                }
                            }
                            //通过统一的重复入院和出院标准进行排除
                            String delReason = getEntrySrv.unifyCheck(aEpisodeID, sdsQcentityEntity.getAbbrev());
                            String ruleIDStr = "";
                            if (StringUtils.isEmpty(delReason) && !exclude.isEmpty()) {
                                //对于符合准入条件，且有排除配置的病例，做自动排除判断
                                for (SdsQcentityRuleEntity sdsQcentityRuleEntity : exclude) {
                                    String ruleDesc = sdsQcentityRuleEntity.getRuleDesc();
                                    // 此类排除条件已在上面统一处理，这里直接跳过
                                    if (ruleDesc.contains("24小时内") || ruleDesc.contains("重复入院")) {
                                        continue;
                                    }
                                    SdsExpressEntity sdsExpressEntity = sdsExpressMapper.selectById(sdsQcentityRuleEntity.getExpressId());
                                    if (!StringUtils.isEmpty(sdsExpressEntity)) {
                                        Class<?> aClass = Class.forName("com.dhcc.sds.base.function.GetEntrySrv");
                                        GetEntrySrv expressFunction = (GetEntrySrv) aClass.newInstance();
                                        Method method = aClass.getMethod(sdsExpressEntity.getExpress(), Long.class, String.class);
                                        ret = (String) method.invoke(expressFunction, aEpisodeID, sdsQcentityRuleEntity.getParam());

                                        if (Objects.equals("Y", ret)) {
                                            ruleIDStr = sdsQcentityRuleEntity.getId() + "";
                                            break;
                                        }
                                    }
                                }
                            }
                            if (!StringUtils.isEmpty(delReason) || !StringUtils.isEmpty(ruleIDStr)) {
                                sdsQcincaseEntity.setOutDate(nowDate);
                                sdsQcincaseEntity.setOutTime(nowDate);
                                sdsQcincaseEntity.setOutDocId(cdcEpisodeEntity.getAdmDoctorId());
                                sdsQcincaseEntity.setState("O");
                                Integer b = sdsQcincaseMapper.updateById(sdsQcincaseEntity);
                                if (b == 1) {
                                    SdsQcincaseOperlogEntity sdsQcincaseOperlogEntity = new SdsQcincaseOperlogEntity();
                                    sdsQcincaseOperlogEntity.setInCaseId(sdsQcincaseEntity.getId());
                                    sdsQcincaseOperlogEntity.setOperState("O");
                                    sdsQcincaseOperlogEntity.setOperUser("系统");
                                    sdsQcincaseOperlogEntity.setOperDate(nowDate);
                                    sdsQcincaseOperlogEntity.setOperReason(ruleIDStr);
                                    sdsQcincaseOperlogEntity.setOperResume(delReason);
                                    Integer insert1 = sdsQcincaseOperlogMapper.insert(sdsQcincaseOperlogEntity);
                                    if (insert1 == 1) {
                                        mrListID = null;
                                        entityDesc = "";
                                        inDate = null;
                                    }
                                }
                            }
                        }
                    } catch (ClassNotFoundException e) {
                        e.printStackTrace();
                        platformTransactionManager.rollback(transactionStatus);
                    }
                    platformTransactionManager.commit(transactionStatus);
                }
            }
            //如果存在门户数据采集程序，更新维度数据
            sdsQcincaseDataService.updatePortalData(mrListID);
        }
        return resultMap;
    }

    public static void main(String[] args) {
        JSONObject.parseObject("");
        ScriptEngineManager manager = new ScriptEngineManager();
        ScriptEngine engine = manager.getEngineByName("JavaScript");
        try {
            engine.put("a", 2);
            System.out.println(engine.eval("a*2"));
            System.out.println(engine.eval("false||2>a"));
            System.out.println(engine.eval("230-120!=10*19"));
            System.out.println(engine.eval("'UTD'!='UTC'"));
            System.out.println(engine.eval("(21240424141)!=4142421414"));
            System.out.println(engine.eval("'UTC'=='UTC'&&'A'=='B'"));
            System.out.println(engine.eval("'UTC'!='UTC'|'A'!='B'"));
            System.out.println(engine.eval("\"1\"==1"));
            System.out.println(engine.eval("(\"a\")==\"a\""));
            System.out.println("*" + engine.eval("\"A\".contains(\"a\")"));
            System.out.println(engine.eval("(\"56\")-(\"23\")>12"));
            System.out.println(engine.eval("!(\"a,b,c\").contains(\"d\") "));
            System.out.println(engine.eval("[2>=1]"));// 这样不行！
            System.out.println(engine.eval("(0)-(72)>1"));
            System.out.println(engine.eval("(\"\")<18"));
            System.out.println(engine.eval("1116.76+27.51+17.58+5.32"));
            System.out.println(engine.eval("0.1+0.2"));
            System.out.println(engine.eval("0.1+0.2==0.3"));
            System.out.println(engine.eval("10+22==32"));
            System.out.println(new BigDecimal("100.23").multiply(BigDecimal.valueOf(100)).longValue());
            System.out.println("a,b".contains(""));
            System.out.println(engine.eval("\'2023-02-28 09:28:32\'==\'2023-02-28 09:28:58\'"));
        } catch (ScriptException e) {
            e.printStackTrace();
        }
    }

    public static void main1(String[] args) {
        JexlContext jc = new MapContext();
        Expression e = new JexlEngine().createExpression("108.00+263.00+104.00+360.00+0.00+1491.00+5.00+205.00+0.00+0.00+0.00+0.00+1116.76+27.51+0.00+0.00+0.00+0.00+0.00+0.00+0.00+17.58+5.32+0.00");
        Object result = e.evaluate(jc);
        System.out.println(result);

        Object res = AviatorEvaluator.execute("108.00+263.00+104.00+360.00+0.00+1491.00+5.00+205.00+0.00+0.00+0.00+0.00+1116.76+27.51+0.00+0.00+0.00+0.00+0.00+0.00+0.00+17.58+5.32+0.00");
        System.out.println(res);
        System.out.println(AviatorEvaluator.execute("0.1+0.2"));
        System.out.println(AviatorEvaluator.execute("10+22==32"));
    }
}
